xref: /aosp_15_r20/external/executorch/backends/qualcomm/runtime/backends/QnnSysImplementation.cpp (revision 523fa7a60841cd1ecfb9cc4201f1ca8b03ed023a)
1 /*
2  * Copyright (c) Qualcomm Innovation Center, Inc.
3  * All rights reserved.
4  *
5  * This source code is licensed under the BSD-style license found in the
6  * LICENSE file in the root directory of this source tree.
7  */
8 
9 #include <dlfcn.h>
10 #include <executorch/backends/qualcomm/runtime/backends/QnnSysImplementation.h>
11 namespace executorch {
12 namespace backends {
13 namespace qnn {
14 
15 using executorch::runtime::Error;
16 
Load()17 Error QnnSystemImplementation::Load() {
18   Qnn_ErrorHandle_t error = QNN_SUCCESS;
19 
20   void* lib_handle_ = dlopen(lib_path_.c_str(), RTLD_NOW | RTLD_LOCAL);
21   if (lib_handle_ == nullptr) {
22     QNN_EXECUTORCH_LOG_ERROR(
23         "Cannot Open QNN library %s, with error: %s",
24         lib_path_.c_str(),
25         dlerror());
26     return Error::Internal;
27   }
28 
29   auto* get_providers =
30       // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
31       reinterpret_cast<QnnSystemInterfaceGetProvidersFn*>(
32           dlsym(lib_handle_, "QnnSystemInterface_getProviders"));
33   if (get_providers == nullptr) {
34     QNN_EXECUTORCH_LOG_ERROR(
35         "QnnSystemImplementation::Load Cannot load symbol "
36         "QnnSystemInterface_getProviders : %s",
37         dlerror());
38     return Error::Internal;
39   }
40 
41   std::uint32_t num_providers;
42   const QnnSystemInterface_t** provider_list = nullptr;
43   error = get_providers(&provider_list, &num_providers);
44   if (error != QNN_SUCCESS) {
45     QNN_EXECUTORCH_LOG_ERROR(
46         "QnnSystemInterface failed to "
47         "get providers. Error %d",
48         QNN_GET_ERROR_CODE(error));
49     return Error::Internal;
50   }
51 
52   if (num_providers != required_num_providers_) {
53     QNN_EXECUTORCH_LOG_ERROR(
54         "QnnSystemInterface Num "
55         "Providers is %d instead of required %d",
56         num_providers,
57         required_num_providers_);
58     return Error::Internal;
59   }
60 
61   qnn_sys_interface_.SetQnnSystemInterface(provider_list[0]);
62 
63   return Error::Ok;
64 }
65 
Unload()66 Error QnnSystemImplementation::Unload() {
67   if (lib_handle_ == nullptr)
68     return Error::Ok;
69 
70   int dlclose_error = dlclose(lib_handle_);
71   if (dlclose_error != 0) {
72     QNN_EXECUTORCH_LOG_WARN(
73         "Failed to close QnnSystem library with error %s", dlerror());
74     return Error::Internal;
75   }
76 
77   lib_handle_ = nullptr;
78 
79   return Error::Ok;
80 }
81 
GetQnnSystemInterface() const82 const QnnSystemInterface& QnnSystemImplementation::GetQnnSystemInterface()
83     const {
84   if (!qnn_sys_interface_.IsLoaded()) {
85     QNN_EXECUTORCH_LOG_WARN(
86         "GetQnnSystemInterface, returning a QNN interface "
87         "which is not loaded yet.");
88   }
89   return qnn_sys_interface_;
90 }
91 } // namespace qnn
92 } // namespace backends
93 } // namespace executorch
94