xref: /aosp_15_r20/external/executorch/backends/qualcomm/runtime/SharedBuffer.h (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 #pragma once
9 #include <QnnTypes.h>
10 #include <executorch/backends/qualcomm/runtime/QnnExecuTorch.h>
11 #include <executorch/runtime/core/error.h>
12 #include <atomic>
13 #include <cstdint>
14 #include <memory>
15 #include <mutex>
16 #include <unordered_map>
17 #include <unordered_set>
18 
19 using RpcMemAllocFn_t = void* (*)(int, uint32_t, int);
20 using RpcMemFreeFn_t = void (*)(void*);
21 using RpcMemToFdFn_t = int (*)(void*);
22 
23 // TODO Finad a better file to place CustomMemTensorInfo
24 bool operator==(const CustomMemTensorInfo& lhs, const CustomMemTensorInfo& rhs);
25 template <>
26 struct std::hash<CustomMemTensorInfo> {
27   std::size_t operator()(const CustomMemTensorInfo& info) const noexcept;
28 };
29 
30 namespace executorch {
31 namespace backends {
32 namespace qnn {
33 
34 class SharedBuffer final {
35  public:
36   SharedBuffer(const SharedBuffer&) = delete;
37   SharedBuffer& operator=(const SharedBuffer&) = delete;
38   SharedBuffer(SharedBuffer&&) = delete;
39   SharedBuffer& operator=(SharedBuffer&&) = delete;
40   ~SharedBuffer();
41 
42   static SharedBuffer& GetSharedBufferManager();
43   void* AllocMem(size_t bytes, size_t alignment);
44   // map a buffer allocated via RPCMem to a file descriptor so it can be
45   // registered with a backend via QnnMem_register()
46   int32_t MemToFd(void* buf);
47 
48   void FreeMem(void* buf);
49 
50   bool IsAllocated(void* buf);
51 
52   bool GetInitialize() {
53     return initialize_;
54   }
55   void SetInitialize(bool initialize) {
56     initialize_ = initialize;
57   }
58 
59   // memory handle is registered during execution
60   void AddCusomMemTensorAddr(void* tensor_addr, void* custom_mem);
61 
62   // memory handle can be registered before execution
63   void AddCusomMemTensorInfo(const CustomMemTensorInfo& info);
64 
65   size_t GetAllocatedSize(void* buf);
66 
67   void* GetCustomMemBase(void* buf);
68 
69   void* GetUnAlignedAddr(void* buf);
70 
71   const std::unordered_set<CustomMemTensorInfo>& GetCustomMemTensorInfoSet() {
72     return custom_mem_tensor_info_set_;
73   };
74 
75  private:
76   SharedBuffer() = default;
77 
78   // dlopen RPCMem library and dlysm required functions
79   executorch::runtime::Error Load();
80 
81   executorch::runtime::Error UnLoad();
82 
83   // Pointer to the dlopen'd libcdsprpc.so shared library which contains
84   // rpcmem_alloc, rpcmem_free, rpcmem_to_fd APIs
85   void* lib_cdsp_rpc_;
86   // Function pointer to rpcmem_alloc
87   RpcMemAllocFn_t rpc_mem_alloc_;
88   // Function pointer to rpcmem_free
89   RpcMemFreeFn_t rpc_mem_free_;
90   // Function pointer to rpcmem_to_fd
91   RpcMemToFdFn_t rpc_mem_to_fd_;
92   std::unordered_map<void*, void*> restore_map_;
93   std::unordered_map<void*, size_t> allocated_size_map_;
94   // Maps for the custom memory
95   std::unordered_map<void*, void*> tensor_addr_to_custom_mem_;
96   std::unordered_set<CustomMemTensorInfo> custom_mem_tensor_info_set_;
97   std::atomic_bool initialize_{false};
98   static std::mutex init_mutex_;
99 };
100 
101 } // namespace qnn
102 } // namespace backends
103 } // namespace executorch
104