ContextMap.java revision 8a0bc0a61e97f8923cb362e1dbb7ff66ffe51507
103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta/* 203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Copyright (C) 2013 The Android Open Source Project 303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * 403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Licensed under the Apache License, Version 2.0 (the "License"); 503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * you may not use this file except in compliance with the License. 603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * You may obtain a copy of the License at 703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * 803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * http://www.apache.org/licenses/LICENSE-2.0 903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * 1003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Unless required by applicable law or agreed to in writing, software 1103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * distributed under the License is distributed on an "AS IS" BASIS, 1203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * See the License for the specific language governing permissions and 1403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * limitations under the License. 1503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 166af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbachpackage com.android.bluetooth.gatt; 1703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 188a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panickerimport android.content.Context; 198a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panickerimport android.os.Binder; 206af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbachimport android.os.IBinder; 216af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbachimport android.os.IBinder.DeathRecipient; 226af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbachimport android.os.IInterface; 236af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbachimport android.os.RemoteException; 2403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battaimport android.util.Log; 2503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battaimport java.util.ArrayList; 266af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbachimport java.util.HashSet; 2703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battaimport java.util.Iterator; 288a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panickerimport java.util.LinkedList; 2903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battaimport java.util.List; 306af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbachimport java.util.NoSuchElementException; 3103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battaimport java.util.Set; 3203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battaimport java.util.UUID; 33f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Aroraimport java.util.HashMap; 34f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Aroraimport java.util.Map; 3503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 3603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta/** 3703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Helper class that keeps track of registered GATT applications. 3803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * This class manages application callbacks and keeps track of GATT connections. 3903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * @hide 4003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 4103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta/*package*/ class ContextMap<T> { 4203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta private static final String TAG = GattServiceConfig.TAG_PREFIX + "ContextMap"; 4303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 4403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 458a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker * ScanStats class helps keep track of information about scans 468a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker * on a per application basis. 478a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker */ 488a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker class ScanStats { 498a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker static final int NUM_SCAN_DURATIONS_KEPT = 5; 508a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 518a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker int scansStarted = 0; 528a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker int scansStopped = 0; 538a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker boolean isScanning = false; 548a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker boolean isRegistered = false; 558a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long minScanTime = Long.MAX_VALUE; 568a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long maxScanTime = 0; 578a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long totalScanTime = 0; 588a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker List<Long> lastScans = new ArrayList<Long>(NUM_SCAN_DURATIONS_KEPT + 1); 598a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long startTime = 0; 608a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long stopTime = 0; 618a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 628a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker void startScan() { 638a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker this.scansStarted++; 648a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker isScanning = true; 658a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker startTime = System.currentTimeMillis(); 668a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 678a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 688a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker void stopScan() { 698a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker this.scansStopped++; 708a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker isScanning = false; 718a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker stopTime = System.currentTimeMillis(); 728a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long currTime = stopTime - startTime; 738a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 748a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker minScanTime = Math.min(currTime, minScanTime); 758a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker maxScanTime = Math.max(currTime, maxScanTime); 768a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker totalScanTime += currTime; 778a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker lastScans.add(currTime); 788a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (lastScans.size() > NUM_SCAN_DURATIONS_KEPT) { 798a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker lastScans.remove(0); 808a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 818a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 828a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 838a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 848a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker /** 8503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Connection class helps map connection IDs to device addresses. 8603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 8703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta class Connection { 8803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta int connId; 8903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta String address; 9003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta int appId; 9103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 9203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Connection(int connId, String address,int appId) { 9303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta this.connId = connId; 9403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta this.address = address; 9503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta this.appId = appId; 9603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 9703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 9803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 9903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 10003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Application entry mapping UUIDs to appIDs and callbacks. 10103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 10203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta class App { 10303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** The UUID of the application */ 10403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta UUID uuid; 10503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 10603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** The id of the application */ 10703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta int id; 10803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 1098a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker /** The package name of the application */ 1108a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker String name; 1118a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 11203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** Application callbacks */ 11303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta T callback; 11403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 1156af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach /** Death receipient */ 1166af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach private IBinder.DeathRecipient mDeathRecipient; 1176af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach 118934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham /** Flag to signal that transport is congested */ 119934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham Boolean isCongested = false; 120934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham 121934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham /** Internal callback info queue, waiting to be send on congestion clear */ 122934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham private List<CallbackInfo> congestionQueue = new ArrayList<CallbackInfo>(); 123934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham 12403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 12503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Creates a new app context. 12603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 1278a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker App(UUID uuid, T callback, String name) { 12803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta this.uuid = uuid; 12903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta this.callback = callback; 1308a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker this.name = name; 13103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 1326af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach 1336af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach /** 1346af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach * Link death recipient 1356af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach */ 1366af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach void linkToDeath(IBinder.DeathRecipient deathRecipient) { 1376af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach try { 1386af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach IBinder binder = ((IInterface)callback).asBinder(); 1396af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach binder.linkToDeath(deathRecipient, 0); 1406af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach mDeathRecipient = deathRecipient; 1416af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } catch (RemoteException e) { 1426af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach Log.e(TAG, "Unable to link deathRecipient for app id " + id); 1436af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 1446af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 1456af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach 1466af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach /** 1476af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach * Unlink death recipient 1486af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach */ 1496af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach void unlinkToDeath() { 1506af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach if (mDeathRecipient != null) { 1516af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach try { 1526af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach IBinder binder = ((IInterface)callback).asBinder(); 1536af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach binder.unlinkToDeath(mDeathRecipient,0); 1546af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } catch (NoSuchElementException e) { 1556af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach Log.e(TAG, "Unable to unlink deathRecipient for app id " + id); 1566af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 1576af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 1586af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 159934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham 160934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham void queueCallback(CallbackInfo callbackInfo) { 161934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham congestionQueue.add(callbackInfo); 162934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham } 163934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham 164934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham CallbackInfo popQueuedCallback() { 165934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham if (congestionQueue.size() == 0) return null; 166934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham return congestionQueue.remove(0); 167934dee789c0c68607a704c5c31ae2e4b956dc227Prerepa Viswanadham } 16803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 16903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 17003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** Our internal application list */ 17103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta List<App> mApps = new ArrayList<App>(); 17203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 1738a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker /** Internal map to keep track of logging information by app name */ 1748a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker HashMap<String, ScanStats> mScanStats = new HashMap<String, ScanStats>(); 1758a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 17603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** Internal list of connected devices **/ 17703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Set<Connection> mConnections = new HashSet<Connection>(); 17803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 17903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 18003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Add an entry to the application context list. 18103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 1828a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker void add(UUID uuid, T callback, Context context) { 1838a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker String appName = context.getPackageManager().getNameForUid( 1848a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker Binder.getCallingUid()); 1858a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (appName == null) { 1868a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker // Assign an app name if one isn't found 1878a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker appName = "Unknown App (UID: " + Binder.getCallingUid() + ")"; 1888a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 1896af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach synchronized (mApps) { 1908a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker mApps.add(new App(uuid, callback, appName)); 1918a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker ScanStats scanStats = mScanStats.get(appName); 1928a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (scanStats == null) { 1938a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker scanStats = new ScanStats(); 1948a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker mScanStats.put(appName, scanStats); 1958a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 1968a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker scanStats.isRegistered = true; 1976af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 19803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 19903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 20003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 2013f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach * Remove the context for a given UUID 2023f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach */ 2033f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach void remove(UUID uuid) { 2043f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach synchronized (mApps) { 2053f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach Iterator<App> i = mApps.iterator(); 2068a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 2073f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach App entry = i.next(); 2083f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach if (entry.uuid.equals(uuid)) { 2093f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach entry.unlinkToDeath(); 2108a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker mScanStats.get(entry.name).isRegistered = false; 2113f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach i.remove(); 2123f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach break; 2133f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach } 2143f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach } 2153f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach } 2163f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach } 2173f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach 2183f8164cd8c4bcce5e79770ee7c02fe00ba9581d5Andre Eisenbach /** 21903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Remove the context for a given application ID. 22003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 22103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta void remove(int id) { 2226af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach synchronized (mApps) { 2236af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach Iterator<App> i = mApps.iterator(); 2248a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 2256af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach App entry = i.next(); 2266af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach if (entry.id == id) { 2276af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach entry.unlinkToDeath(); 2288a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker mScanStats.get(entry.name).isRegistered = false; 2296af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach i.remove(); 2306af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach break; 2316af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 23203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 23303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 23403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 23503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 23603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 23703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Add a new connection for a given application ID. 23803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 23903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta void addConnection(int id, int connId, String address) { 2406af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach synchronized (mConnections) { 2416af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach App entry = getById(id); 2426af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach if (entry != null){ 2436af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach mConnections.add(new Connection(connId, address, id)); 2446af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 24503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 24603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 24703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 24803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 24903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Remove a connection with the given ID. 25003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 25103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta void removeConnection(int id, int connId) { 2526af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach synchronized (mConnections) { 2536af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach Iterator<Connection> i = mConnections.iterator(); 2548a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 2556af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach Connection connection = i.next(); 2566af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach if (connection.connId == connId) { 2576af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach i.remove(); 2586af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach break; 2596af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 26003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 26103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 26203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 26303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 26403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 26503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Get an application context by ID. 26603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 26703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta App getById(int id) { 26803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Iterator<App> i = mApps.iterator(); 2698a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 27003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta App entry = i.next(); 27103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta if (entry.id == id) return entry; 27203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 27303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Log.e(TAG, "Context not found for ID " + id); 27403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return null; 27503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 27603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 27703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 27803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Get an application context by UUID. 27903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 28003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta App getByUuid(UUID uuid) { 28103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Iterator<App> i = mApps.iterator(); 2828a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 28303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta App entry = i.next(); 28403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta if (entry.uuid.equals(uuid)) return entry; 28503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 28603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Log.e(TAG, "Context not found for UUID " + uuid); 28703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return null; 28803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 28903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 29003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 2918a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker * Get an application context by the calling Apps name. 2928a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker */ 2938a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker App getByName(String name) { 2948a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker Iterator<App> i = mApps.iterator(); 2958a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 2968a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker App entry = i.next(); 2978a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (entry.name.equals(name)) return entry; 2988a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 2998a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker Log.e(TAG, "Context not found for name " + name); 3008a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker return null; 3018a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 3028a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 3038a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker /** 3048a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker * Get Logging info by ID 3058a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker */ 3068a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker ScanStats getScanStatsById(int id) { 3078a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker App temp = getById(id); 3088a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (temp != null) { 3098a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker return mScanStats.get(temp.name); 3108a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 3118a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker return null; 3128a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 3138a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 3148a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker /** 31503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Get the device addresses for all connected devices 31603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 31703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Set<String> getConnectedDevices() { 31803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Set<String> addresses = new HashSet<String>(); 31903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Iterator<Connection> i = mConnections.iterator(); 3208a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 32103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Connection connection = i.next(); 32203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta addresses.add(connection.address); 32303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 32403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return addresses; 32503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 32603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 32703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 32803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Get an application context by a connection ID. 32903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 33003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta App getByConnId(int connId) { 33103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Iterator<Connection> ii = mConnections.iterator(); 3328a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (ii.hasNext()) { 33303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Connection connection = ii.next(); 33403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta if (connection.connId == connId){ 33503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return getById(connection.appId); 33603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 33703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 33803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return null; 33903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 34003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 34103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 34203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Returns a connection ID for a given device address. 34303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 34403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Integer connIdByAddress(int id, String address) { 34503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta App entry = getById(id); 34603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta if (entry == null) return null; 34703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 34803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Iterator<Connection> i = mConnections.iterator(); 3498a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 35003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Connection connection = i.next(); 35103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta if (connection.address.equals(address) && connection.appId == id) 35203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return connection.connId; 35303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 35403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return null; 35503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 35603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 35703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 35803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Returns the device address for a given connection ID. 35903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 36003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta String addressByConnId(int connId) { 36103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Iterator<Connection> i = mConnections.iterator(); 3628a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 36303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Connection connection = i.next(); 36403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta if (connection.connId == connId) return connection.address; 36503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 36603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return null; 36703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 36803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 36903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta List<Connection> getConnectionByApp(int appId) { 37003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta List<Connection> currentConnections = new ArrayList<Connection>(); 37103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Iterator<Connection> i = mConnections.iterator(); 3728a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 37303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta Connection connection = i.next(); 37403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta if (connection.appId == appId) 37503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta currentConnections.add(connection); 37603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 37703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta return currentConnections; 37803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 37903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 38003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 38103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Erases all application context entries. 38203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 38303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta void clear() { 3846af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach synchronized (mApps) { 3856af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach Iterator<App> i = mApps.iterator(); 3868a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 3876af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach App entry = i.next(); 3886af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach entry.unlinkToDeath(); 3896af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach i.remove(); 3906af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 3916af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 3926af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach 3936af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach synchronized (mConnections) { 3946af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach mConnections.clear(); 3956af1f25031e4378efb1a4fc286974c1038a357baAndre Eisenbach } 39603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 39703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 39803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta /** 399f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora * Returns connect device map with addr and appid 400f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora */ 401f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora Map<Integer, String> getConnectedMap(){ 402f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora Map<Integer, String> connectedmap = new HashMap<Integer, String>(); 403f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora for(Connection conn: mConnections){ 404f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora connectedmap.put(conn.appId, conn.address); 405f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora } 406f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora return connectedmap; 407f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora } 408f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora 409f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora /** 41003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta * Logs debug information. 41103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta */ 412a02de6484f9b6cac6b8c811edae11be55746b555Andre Eisenbach void dump(StringBuilder sb) { 4138a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long currTime = System.currentTimeMillis(); 41403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 4158a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" Entries: " + mScanStats.size() + "\n\n"); 4168a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4178a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker Iterator<Map.Entry<String,ScanStats>> i = mScanStats.entrySet().iterator(); 4188a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while (i.hasNext()) { 4198a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker Map.Entry<String, ScanStats> entry = i.next(); 42003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 4218a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker String name = entry.getKey(); 4228a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker ScanStats scanStats = entry.getValue(); 42303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 4248a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long maxScanTime = scanStats.maxScanTime; 4258a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long minScanTime = scanStats.minScanTime; 4268a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long currScanTime = 0; 4278a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4288a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (scanStats.isScanning) { 4298a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker currScanTime = currTime - scanStats.startTime; 4308a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker minScanTime = Math.min(currScanTime, minScanTime); 4318a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker maxScanTime = Math.max(currScanTime, maxScanTime); 4328a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 4338a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4348a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (minScanTime == Long.MAX_VALUE) { 4358a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker minScanTime = 0; 4368a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 4378a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4388a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long lastScan = 0; 4398a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (scanStats.stopTime != 0) { 4408a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker lastScan = currTime - scanStats.stopTime; 4418a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 4428a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4438a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker long avgScanTime = 0; 4448a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (scanStats.scansStarted > 0) { 4458a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker avgScanTime = (scanStats.totalScanTime + currScanTime) / 4468a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker scanStats.scansStarted; 4478a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 4488a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4498a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" Application Name: " + name); 4508a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (scanStats.isRegistered) sb.append(" (Registered)"); 4518a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append("\n"); 4528a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4538a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" LE scans (started/stopped) : " + 4548a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker scanStats.scansStarted + " / " + 4558a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker scanStats.scansStopped + "\n"); 4568a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" Scan time in ms (min/max/avg) : " + 4578a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker minScanTime + " / " + 4588a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker maxScanTime + " / " + 4598a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker avgScanTime + "\n"); 4608a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4618a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" Time since last scan ended in ms : " + lastScan + "\n"); 4628a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4638a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" Last " + scanStats.lastScans.size() + 4648a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker " scans in ms (oldest first): "); 4658a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker for (Long time : scanStats.lastScans) { 4668a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(time + " "); 4678a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 4688a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append("\n"); 4698a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4708a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (scanStats.isRegistered) { 4718a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker App appEntry = getByName(name); 4728a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" Application ID : " + 4738a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker appEntry.id + "\n"); 4748a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" UUID : " + 4758a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker appEntry.uuid + "\n"); 4768a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4778a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker if (scanStats.isScanning) { 4788a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" Current scan duration : " + 4798a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker currScanTime + "\n"); 4808a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 4818a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4828a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker List<Connection> connections = getConnectionByApp(appEntry.id); 4838a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" Connections: " + connections.size() + "\n"); 4848a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker 4858a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker Iterator<Connection> ii = connections.iterator(); 4868a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker while(ii.hasNext()) { 4878a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker Connection connection = ii.next(); 4888a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append(" " + connection.connId + ": " + 4898a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker connection.address + "\n"); 4908a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker } 49103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 4928a0bc0a61e97f8923cb362e1dbb7ff66ffe51507Ajay Panicker sb.append("\n"); 49303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 49403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta } 49503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta} 496