#鸿蒙通关秘籍#如何在TaskPool子线程中预加载So库并调用其函数?

HarmonyOS
1天前
浏览
收藏 0
回答 1
待解决
回答 1
按赞同
/
按时间
SQL暗影幽魂

在HarmonyOS NEXT中,可以在TaskPool子线程中预加载.so库并调用其中的函数。以下是具体的实现步骤:

  1. 在工程中放置所需的.so文件,并在CMakeLists中通过target_link_directories命令将包含这些库文件的目录添加到预加载库的链接目录:

    target_link_directories(preloadso PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/../../../libs/${OHOS_ARCH}/)
    
  2. 通过target_link_libraries命令链接需要预加载的so库到项目中:

    target_link_libraries(preloadso PUBLIC libhilog_ndk.z.so libace_napi.z.so global_handlers libnativerawfile.so)
    
  3. 定义全局对象global_handlers以存放加载so库所得的句柄:

    std::unordered_map<std::string, void *> global_handlers;
    
  4. 在Native层的Preload接口中,遍历传入的.so路径数组,使用dlopen函数加载库,并将句柄保存到global_handlers中:

    void *handler = dlopen(path, RTLD_LAZY);
    if (handler != nullptr) {
        global_handlers[std::string(path)] = handler;
    }
    
  5. ArkTS层使用TaskPool创建子线程,通过preloadSO接口调用Native层的Preload接口,实现子线程加载.so库,并导出preloadSOByTaskPool函数。

    @Concurrent
    function preloadSO(): string[] {
      return napi.preload(Constants.LIBRARY_PATH_ARRAY);
    }
    export function preloadSOByTaskPool(): void {
      let task: taskpool.Task = new taskpool.Task(preloadSO);
      try {
        taskpool.execute(task, taskpool.Priority.HIGH).then((res: string[]) => {
            logger.info(TAG, '%{public}s', 'PreloadSOByTaskPool:' + JSON.stringify(res));
        })
      } catch (err) {
         logger.error(TAG, "PreloadSOByTaskPool: execute failed, " + (err as BusinessError).toString());
      }
    }
    
  6. 在Ability的onCreate方法中,调用preloadSOByTaskPool以开启子线程,完成库的预加载。

    onCreate(want: Want, launchParam: AbilityConstant.LaunchParam): void {
        preloadSOByTaskPool();
    }
    

通过上述步骤,可以在TaskPool子线程中高效地预加载.so库并调用其内部的函数。

分享
微博
QQ
微信
回复
1天前
相关问题
如何在Native层加载so
1077浏览 • 1回复 待解决
TaskPool线程和主线程如何通信
2279浏览 • 1回复 待解决
如何在ArkTS动态加载so
438浏览 • 1回复 待解决