1 /* Copyright 2020 The TensorFlow Authors. All Rights Reserved.
2
3 Licensed under the Apache License, Version 2.0 (the "License");
4 you may not use this file except in compliance with the License.
5 You may obtain a copy of the License at
6
7 http://www.apache.org/licenses/LICENSE-2.0
8
9 Unless required by applicable law or agreed to in writing, software
10 distributed under the License is distributed on an "AS IS" BASIS,
11 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 See the License for the specific language governing permissions and
13 limitations under the License.
14 ==============================================================================*/
15 #include <dlfcn.h>
16 #include <fcntl.h>
17 #include <stdint.h>
18 #include <sys/stat.h>
19
20 #include <cstdio>
21 #include <cstring>
22
23 #include "tensorflow/lite/delegates/hexagon/hexagon_nn/hexagon_nn.h"
24 #include "tensorflow/lite/delegates/hexagon/hexagon_nn/soc_model.h"
25
26 namespace {
27
LoadLibadsprpc()28 void* LoadLibadsprpc() {
29 void* lib = dlopen("libadsprpc.so", RTLD_LAZY | RTLD_LOCAL);
30 if (lib) {
31 fprintf(stdout, "loaded libadsprpc.so\n");
32 return lib;
33 }
34
35 return nullptr;
36 }
37
LoadLibcdsprpc()38 void* LoadLibcdsprpc() {
39 void* lib = dlopen("libcdsprpc.so", RTLD_LAZY | RTLD_LOCAL);
40 if (lib) {
41 fprintf(stdout, "loaded libcdsprpc.so\n");
42 return lib;
43 }
44
45 return nullptr;
46 }
47
LoadDsprpc()48 void* LoadDsprpc() {
49 SocSkelTable soc_model = tflite::delegates::getsoc_model();
50 // Use aDSP for 835 and 820, otherwise cDSP.
51 if (soc_model.mode == NON_DOMAINS ||
52 (soc_model.dsp_type != nullptr &&
53 strcmp(soc_model.dsp_type, "adsp") == 0)) {
54 return LoadLibadsprpc();
55 }
56 return LoadLibcdsprpc();
57 }
58
LoadFunction(const char * name)59 void* LoadFunction(const char* name) {
60 static void* libadsprpc = LoadDsprpc();
61 if (libadsprpc == nullptr) {
62 fprintf(stderr, "libadsprpc handle is NULL\n");
63 return nullptr;
64 }
65 auto* func_pt = dlsym(libadsprpc, name);
66 if (func_pt == nullptr) {
67 fprintf(stderr, "Func %s not available on this device (NULL).\n", name);
68 }
69 return func_pt;
70 }
71
72 using remote_handle_open_fn = decltype(remote_handle_open);
73 using remote_handle64_open_fn = decltype(remote_handle64_open);
74 using remote_handle_invoke_fn = decltype(remote_handle_invoke);
75 using remote_handle64_invoke_fn = decltype(remote_handle64_invoke);
76 using remote_handle_close_fn = decltype(remote_handle_close);
77 using remote_handle64_close_fn = decltype(remote_handle64_close);
78 using remote_mmap_fn = decltype(remote_mmap);
79 using remote_mmap64_fn = decltype(remote_mmap64);
80 using remote_munmap_fn = decltype(remote_munmap);
81 using remote_munmap64_fn = decltype(remote_munmap64);
82 using remote_register_buf_fn = decltype(remote_register_buf);
83 using remote_set_mode_fn = decltype(remote_set_mode);
84 using remote_handle_control_fn = decltype(remote_handle_control);
85
86 struct AdsprpcInterface {
87 remote_handle_open_fn* handle_open_fn =
88 reinterpret_cast<remote_handle_open_fn*>(
89 LoadFunction("remote_handle_open"));
90 remote_handle64_open_fn* handle64_open_fn =
91 reinterpret_cast<remote_handle64_open_fn*>(
92 LoadFunction("remote_handle64_open"));
93 remote_handle_invoke_fn* handle_invoke_fn =
94 reinterpret_cast<remote_handle_invoke_fn*>(
95 LoadFunction("remote_handle_invoke"));
96 remote_handle64_invoke_fn* handle64_invoke_fn =
97 reinterpret_cast<remote_handle64_invoke_fn*>(
98 LoadFunction("remote_handle64_invoke"));
99 remote_handle_close_fn* handle_close_fn =
100 reinterpret_cast<remote_handle_close_fn*>(
101 LoadFunction("remote_handle_close"));
102 remote_handle64_close_fn* handle64_close_fn =
103 reinterpret_cast<remote_handle64_close_fn*>(
104 LoadFunction("remote_handle64_close"));
105 remote_handle_control_fn* handle_control_fn =
106 reinterpret_cast<remote_handle_control_fn*>(
107 LoadFunction("remote_handle_control"));
108 remote_mmap_fn* mmap_fn =
109 reinterpret_cast<remote_mmap_fn*>(LoadFunction("remote_mmap"));
110 remote_munmap_fn* munmap_fn =
111 reinterpret_cast<remote_munmap_fn*>(LoadFunction("remote_munmap"));
112 remote_mmap64_fn* mmap64_fn =
113 reinterpret_cast<remote_mmap64_fn*>(LoadFunction("remote_mmap64"));
114 remote_munmap64_fn* munmap64_fn =
115 reinterpret_cast<remote_munmap64_fn*>(LoadFunction("remote_munmap64"));
116 remote_register_buf_fn* register_buf_fn =
117 reinterpret_cast<remote_register_buf_fn*>(
118 LoadFunction("remote_register_buf"));
119 remote_set_mode_fn* set_mode_fn =
120 reinterpret_cast<remote_set_mode_fn*>(LoadFunction("remote_set_mode"));
121
122 // Returns singleton instance.
Singleton__anon8dddd1f20111::AdsprpcInterface123 static AdsprpcInterface* Singleton() {
124 static AdsprpcInterface* instance = new AdsprpcInterface();
125 return instance;
126 }
127 };
128
129 } // namespace
130
131 extern "C" {
remote_handle_open(const char * name,remote_handle * h)132 int remote_handle_open(const char* name, remote_handle* h) {
133 return AdsprpcInterface::Singleton()->handle_open_fn
134 ? AdsprpcInterface::Singleton()->handle_open_fn(name, h)
135 : -1;
136 }
137
remote_handle64_open(const char * name,remote_handle64 * h)138 int remote_handle64_open(const char* name, remote_handle64* h) {
139 return AdsprpcInterface::Singleton()->handle64_open_fn
140 ? AdsprpcInterface::Singleton()->handle64_open_fn(name, h)
141 : -1;
142 }
143
remote_handle_invoke(remote_handle h,uint32_t scalars,remote_arg * args)144 int remote_handle_invoke(remote_handle h, uint32_t scalars, remote_arg* args) {
145 return AdsprpcInterface::Singleton()->handle_invoke_fn
146 ? AdsprpcInterface::Singleton()->handle_invoke_fn(h, scalars, args)
147 : -1;
148 }
149
remote_handle64_invoke(remote_handle64 h,uint32_t scalars,remote_arg * args)150 int remote_handle64_invoke(remote_handle64 h, uint32_t scalars,
151 remote_arg* args) {
152 return AdsprpcInterface::Singleton()->handle64_invoke_fn
153 ? AdsprpcInterface::Singleton()->handle64_invoke_fn(h, scalars,
154 args)
155 : -1;
156 }
157
remote_handle_close(remote_handle h)158 int remote_handle_close(remote_handle h) {
159 return AdsprpcInterface::Singleton()->handle_close_fn
160 ? AdsprpcInterface::Singleton()->handle_close_fn(h)
161 : -1;
162 }
163
remote_handle64_close(remote_handle64 h)164 int remote_handle64_close(remote_handle64 h) {
165 return AdsprpcInterface::Singleton()->handle64_close_fn
166 ? AdsprpcInterface::Singleton()->handle64_close_fn(h)
167 : -1;
168 }
169
remote_handle_control(uint32_t req,void * data,uint32_t datalen)170 int remote_handle_control(uint32_t req, void* data, uint32_t datalen) {
171 return AdsprpcInterface::Singleton()->handle_control_fn
172 ? AdsprpcInterface::Singleton()->handle_control_fn(req, data,
173 datalen)
174 : -1;
175 }
176
remote_mmap(int fd,uint32_t flags,uint32_t addr,int size,uint32_t * result)177 int remote_mmap(int fd, uint32_t flags, uint32_t addr, int size,
178 uint32_t* result) {
179 return AdsprpcInterface::Singleton()->mmap_fn
180 ? AdsprpcInterface::Singleton()->mmap_fn(fd, flags, addr, size,
181 result)
182 : -1;
183 }
184
remote_mmap64(int fd,uint32_t flags,uintptr_t vaddrin,int64_t size,uintptr_t * vaddrout)185 int remote_mmap64(int fd, uint32_t flags, uintptr_t vaddrin, int64_t size,
186 uintptr_t* vaddrout) {
187 return AdsprpcInterface::Singleton()->mmap64_fn
188 ? AdsprpcInterface::Singleton()->mmap64_fn(fd, flags, vaddrin,
189 size, vaddrout)
190 : -1;
191 }
192
remote_munmap(uint32_t addr,int size)193 int remote_munmap(uint32_t addr, int size) {
194 return AdsprpcInterface::Singleton()->munmap_fn
195 ? AdsprpcInterface::Singleton()->munmap_fn(addr, size)
196 : -1;
197 }
198
remote_munmap64(uintptr_t vaddrout,int64_t size)199 int remote_munmap64(uintptr_t vaddrout, int64_t size) {
200 return AdsprpcInterface::Singleton()->munmap64_fn
201 ? AdsprpcInterface::Singleton()->munmap64_fn(vaddrout, size)
202 : -1;
203 }
204
remote_register_buf(void * buf,int size,int fd)205 void remote_register_buf(void* buf, int size, int fd) {
206 if (AdsprpcInterface::Singleton()->register_buf_fn) {
207 AdsprpcInterface::Singleton()->register_buf_fn(buf, size, fd);
208 }
209 }
210
remote_set_mode(uint32_t mode)211 int remote_set_mode(uint32_t mode) {
212 return AdsprpcInterface::Singleton()->set_mode_fn
213 ? AdsprpcInterface::Singleton()->set_mode_fn(mode)
214 : -1;
215 }
216
217 } // extern "C"
218