Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 94cca9e8 authored by Andre Eisenbach's avatar Andre Eisenbach Committed by Android Git Automerger
Browse files

am 03f841c7: Add binder DeathRecipient to GATT service

* commit '03f841c7':
  Add binder DeathRecipient to GATT service
parents ec1dc053 03f841c7
Loading
Loading
Loading
Loading
+74 −22
Original line number Diff line number Diff line
@@ -13,15 +13,18 @@
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.android.bluetooth.gatt;


import android.os.IBinder;
import android.os.IBinder.DeathRecipient;
import android.os.IInterface;
import android.os.RemoteException;
import android.util.Log;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.HashSet;
import java.util.NoSuchElementException;
import java.util.Set;
import java.util.UUID;

@@ -61,6 +64,9 @@ import java.util.UUID;
        /** Application callbacks */
        T callback;

        /** Death receipient */
        private IBinder.DeathRecipient mDeathRecipient;

        /**
         * Creates a new app context.
         */
@@ -68,6 +74,33 @@ import java.util.UUID;
            this.uuid = uuid;
            this.callback = callback;
        }

        /**
         * Link death recipient
         */
        void linkToDeath(IBinder.DeathRecipient deathRecipient) {
            try {
                IBinder binder = ((IInterface)callback).asBinder();
                binder.linkToDeath(deathRecipient, 0);
                mDeathRecipient = deathRecipient;
            } catch (RemoteException e) {
                Log.e(TAG, "Unable to link deathRecipient for app id " + id);
            }
        }

        /**
         * Unlink death recipient
         */
        void unlinkToDeath() {
            if (mDeathRecipient != null) {
                try {
                    IBinder binder = ((IInterface)callback).asBinder();
                    binder.unlinkToDeath(mDeathRecipient,0);
                } catch (NoSuchElementException e) {
                    Log.e(TAG, "Unable to unlink deathRecipient for app id " + id);
                }
            }
        }
    }

    /** Our internal application list */
@@ -80,37 +113,45 @@ import java.util.UUID;
     * Add an entry to the application context list.
     */
    void add(UUID uuid, T callback) {
        synchronized (mApps) {
            mApps.add(new App(uuid, callback));
        }
    }

    /**
     * Remove the context for a given application ID.
     */
    void remove(int id) {
        synchronized (mApps) {
            Iterator<App> i = mApps.iterator();
            while(i.hasNext()) {
                App entry = i.next();
                if (entry.id == id) {
                    entry.unlinkToDeath();
                    i.remove();
                    break;
                }
            }
        }
    }

    /**
     * Add a new connection for a given application ID.
     */
    void addConnection(int id, int connId, String address) {
        synchronized (mConnections) {
            App entry = getById(id);
            if (entry != null){
                mConnections.add(new Connection(connId, address, id));
            }
        }
    }

    /**
     * Remove a connection with the given ID.
     */
    void removeConnection(int id, int connId) {
        synchronized (mConnections) {
            Iterator<Connection> i = mConnections.iterator();
            while(i.hasNext()) {
                Connection connection = i.next();
@@ -120,6 +161,7 @@ import java.util.UUID;
                }
            }
        }
    }

    /**
     * Get an application context by ID.
@@ -217,9 +259,19 @@ import java.util.UUID;
     * Erases all application context entries.
     */
    void clear() {
        mApps.clear();
        synchronized (mApps) {
            Iterator<App> i = mApps.iterator();
            while(i.hasNext()) {
                App entry = i.next();
                entry.unlinkToDeath();
                i.remove();
            }
        }

        synchronized (mConnections) {
            mConnections.clear();
        }
    }

    /**
     * Logs debug information.
+39 −4
Original line number Diff line number Diff line
@@ -20,7 +20,12 @@ import android.app.Service;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothProfile;
import android.bluetooth.IBluetoothGatt;
import android.bluetooth.IBluetoothGattCallback;
import android.bluetooth.IBluetoothGattServerCallback;
import android.content.Intent;
import android.os.IBinder;
import android.os.IBinder.DeathRecipient;
import android.os.ParcelUuid;
import android.os.RemoteException;
import android.util.Log;
@@ -36,9 +41,6 @@ import java.util.UUID;

import com.android.bluetooth.btservice.ProfileService;
import com.android.bluetooth.btservice.ProfileService.IProfileServiceBinder;
import android.bluetooth.IBluetoothGatt;
import android.bluetooth.IBluetoothGattCallback;
import android.bluetooth.IBluetoothGattServerCallback;

/**
 * Provides Bluetooth Gatt profile, as a service in
@@ -180,6 +182,37 @@ public class GattService extends ProfileService {
        return super.onStartCommand(intent, flags, startId);
    }

    /**
     * DeathReceipient handlers used to unregister applications that
     * disconnect ungracefully (ie. crash or forced close).
     */

    class ClientDeathRecipient implements IBinder.DeathRecipient {
        int mAppIf;

        public ClientDeathRecipient(int appIf) {
            mAppIf = appIf;
        }

        public void binderDied() {
            if (DBG) Log.d(TAG, "Binder is dead - unregistering client (" + mAppIf + ")!");
            unregisterClient(mAppIf);
        }
    }

    class ServerDeathRecipient implements IBinder.DeathRecipient {
        int mAppIf;

        public ServerDeathRecipient(int appIf) {
            mAppIf = appIf;
        }

        public void binderDied() {
            if (DBG) Log.d(TAG, "Binder is dead - unregistering server (" + mAppIf + ")!");
            unregisterServer(mAppIf);
        }
    }

    /**
     * Handlers for incoming service calls
     */
@@ -494,6 +527,7 @@ public class GattService extends ProfileService {
        ClientMap.App app = mClientMap.getByUuid(uuid);
        if (app != null) {
            app.id = clientIf;
            app.linkToDeath(new ClientDeathRecipient(clientIf));
            app.callback.onClientRegistered(status, clientIf);
        }
    }
@@ -882,7 +916,7 @@ public class GattService extends ProfileService {
    }

    void clientConnect(int clientIf, String address, boolean isDirect) {
        if (DBG) Log.d(TAG, "clientConnect() - address=" + address);
        if (DBG) Log.d(TAG, "clientConnect() - address=" + address + ", isDirect=" + isDirect);
        gattClientConnectNative(clientIf, address, isDirect);
    }

@@ -1037,6 +1071,7 @@ public class GattService extends ProfileService {
        ServerMap.App app = mServerMap.getByUuid(uuid);
        if (app != null) {
            app.id = serverIf;
            app.linkToDeath(new ServerDeathRecipient(serverIf));
            app.callback.onServerRegistered(status, serverIf);
        }
    }