IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 移动开发 -> hidl之client/server端的双向死亡监听 -> 正文阅读

[移动开发]hidl之client/server端的双向死亡监听

我们在AIDL跨进程通信中知道,可以通过Binder的linkToDeath()实现client/server端的双向死亡监听。那么HIDL可以吗?本文以Android应用为client端,Hal Service为server端。一起看看吧~~

基础知识参考官方文档。https://source.android.com/docs/core/architecture/hidl(打不开链接的小伙伴,不可能是长得太帅)

1.Server端

TestManager继承了类 hidl_death_recipient并重新它的serviceDied方法,从而实现死亡监听。

TestManager.h中部分代码:

class TestManager : public hidl_death_recipient {

        ...
        void serviceDied(uint64_t cookie, const android::wp<::android::hidl::base::V1_0::IBase>& who) override;
        ...
};

TestManager.cpp中部分代码:

//register callback and return cookie id
int32_t TestManager::subscribe(const sp<ITestServerCallback>& callback) {
    ALOGI("TestManager subscribe, callback=%p\n", callback.get());
    lock_guard<mutex> lk(mMut);
    ALOGI("TestManager subscribe>>>mDeathCount =%lu\n", mDeathCount);
    int32_t cookie = 0;
    mCallbackMap.insert(std::pair<int, sp<ITestServerCallback>>(mDeathCount, callback));
    if (mChd != nullptr) {
        ALOGI("TestManager subscribe>>>linkToDeath\n");
        callback->linkToDeath(mChd, mDeathCount);
        cookie = mDeathCount;
        mDeathCount++;
    } else {
        ALOGI("TestManager mChd is null\n");
    }
    return cookie;
}

//unregister callback by cookie id
int32_t TestManager::unsubscribe(int32_t cookie) {
    ALOGI("TestManager unsubscribe, cookie=%d\n", cookie);
    int result = mCallbackMap.erase(cookie);
    ALOGI("TestManager unsubscribe result is %d", result);
    return cookie;
}

//listening service died
void TestManager::serviceDied(uint64_t cookie, const android::wp<::android::hidl::base::V1_0::IBase>& /*who*/) {
    lock_guard<mutex> lk(mMut);
    ALOGI("TestManager serviceDied cookie is %lu, callbackMap size is %lu\n", cookie , mCallbackMap.size());
    int result = mCallbackMap.erase(cookie);
    ALOGI("TestManager erase result is %d", result);
}

2.Client端

2.1.获取service实例

private IHwBinder.DeathRecipient mDeathDecipient = new IHwBinder.DeathRecipient() {
   @Override public void serviceDied(long cookie) {
     try {
       Log.d(TAG, "mService serviceDied cookie = " + cookie);
       mService.asBinder().unlinkToDeath(this);
     } catch (Exception e) {
       e.printStackTrace();
     }
   }
 };
 
private void initHalService() {
  try {
    mService = ITestServer.getService();
    mService.asBinder().linkToDeath(mDeathDecipient, 42);
  } catch (Exception e) {
    Toast.makeText(this, e.toString(), Toast.LENGTH_SHORT).show();
  }
}

2.2.Callback的注册、注销

if (v.getId() == R.id.subscribe) {
  try {
    if (mCallback == null) {
      mCallback = new MyCallback();
    }
    Log.d(TAG, "subscribe mCallback = " + mCallback);
    int cookie = mService.subscribe(mCallback);
    cookieList.add(cookie);
  } catch (Exception e) {
    e.printStackTrace();
  }
} else if (v.getId() == R.id.unsubscribe) {
  try {
    Iterator<Integer> iterator = cookieList.iterator();
    while (iterator.hasNext()) {
      int cookie = iterator.next();
      Log.d(TAG, "unsubscribe cookie = " + cookie);
      if (cookie != 0) {
        mService.unsubscribe(cookie);
        iterator.remove();
      }
    }
  } catch (Exception e) {
    e.printStackTrace();
  }
}

3.运行结果

3.1.正常注册、注销

log如下:

09-23 19:22:11.374 7974 7974 D TestManager: subscribe mCallback = vendor.test.testserver@1.0::ITestServerCallback@Stub
09-23 19:22:11.390 8005 8007 I : TestManager subscribe, callback=0x70bf25b380
09-23 19:22:11.390 8005 8007 I : TestManager subscribe>>>mDeathCount =1
09-23 19:22:11.390 8005 8007 I : TestManager subscribe>>>linkToDeath
09-23 19:22:14.321 7974 7974 D TestManager: unsubscribe cookie = 1
09-23 19:22:14.322 8005 8007 I : TestManager unsubscribe, cookie=1
09-23 19:22:14.326 8005 8007 I : TestManager unsubscribe result is 1

3.2.Client异常退出

log如下:

09-23 19:23:23.669 7974 7974 D TestManager: subscribe mCallback = vendor.test.testserver@1.0::ITestServerCallback@Stub
09-23 19:23:23.670 8005 8007 I : TestManager subscribe, callback=0x70bf25b380
09-23 19:23:23.670 8005 8007 I : TestManager subscribe>>>mDeathCount =2
09-23 19:23:23.670 8005 8007 I : TestManager subscribe>>>linkToDeath
09-23 19:23:30.171 8005 8007 I : TestManager serviceDied cookie is 2, callbackMap size is 1
09-23 19:23:30.171 8005 8007 I : TestManager erase result is 1

3.3.Server异常退出

log如下:

09-23 19:24:24.457 8011 8011 D TestManager: subscribe mCallback = vendor.test.testserver@1.0::ITestServerCallback@Stub
09-23 19:24:24.483 8005 8007 I : TestManager subscribe, callback=0x70bf25b380
09-23 19:24:24.483 8005 8007 I : TestManager subscribe>>>mDeathCount =3
09-23 19:24:24.483 8005 8007 I : TestManager subscribe>>>linkToDeath
09-23 19:24:28.544 8011 8036 D TestManager: mService serviceDied cookie = 42

4.完整代码

https://gitee.com/lxy0502/hidl-usage

如有问题,欢迎留言~~

  移动开发 最新文章
Vue3装载axios和element-ui
android adb cmd
【xcode】Xcode常用快捷键与技巧
Android开发中的线程池使用
Java 和 Android 的 Base64
Android 测试文字编码格式
微信小程序支付
安卓权限记录
知乎之自动养号
【Android Jetpack】DataStore
上一篇文章      下一篇文章      查看所有文章
加:2022-09-25 23:17:16  更:2022-09-25 23:17:47 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年5日历 -2024/5/19 22:22:52-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码