Warning: This file is not a C or C++ file. It does not have highlighting.

1//===-- PluginManager.h - Plugin loading and communication API --*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// Declarations for managing devices that are handled by RTL plugins.
10//
11//===----------------------------------------------------------------------===//
12
13#ifndef OMPTARGET_PLUGIN_MANAGER_H
14#define OMPTARGET_PLUGIN_MANAGER_H
15
16#include "PluginInterface.h"
17
18#include "DeviceImage.h"
19#include "ExclusiveAccess.h"
20#include "Shared/APITypes.h"
21#include "Shared/Requirements.h"
22
23#include "device.h"
24
25#include "llvm/ADT/DenseSet.h"
26#include "llvm/ADT/SmallVector.h"
27#include "llvm/ADT/iterator.h"
28#include "llvm/ADT/iterator_range.h"
29#include "llvm/Support/DynamicLibrary.h"
30#include "llvm/Support/Error.h"
31
32#include <cstdint>
33#include <list>
34#include <memory>
35#include <mutex>
36#include <string>
37
38using GenericPluginTy = llvm::omp::target::plugin::GenericPluginTy;
39
40/// Struct for the data required to handle plugins
41struct PluginManager {
42 /// Type of the devices container. We hand out DeviceTy& to queries which are
43 /// stable addresses regardless if the container changes.
44 using DeviceContainerTy = llvm::SmallVector<std::unique_ptr<DeviceTy>>;
45
46 /// Exclusive accessor type for the device container.
47 using ExclusiveDevicesAccessorTy = Accessor<DeviceContainerTy>;
48
49 PluginManager() {}
50
51 void init();
52
53 void deinit();
54
55 // Register a shared library with all (compatible) RTLs.
56 void registerLib(__tgt_bin_desc *Desc);
57
58 // Unregister a shared library from all RTLs.
59 void unregisterLib(__tgt_bin_desc *Desc);
60
61 void addDeviceImage(__tgt_bin_desc &TgtBinDesc,
62 __tgt_device_image &TgtDeviceImage) {
63 DeviceImages.emplace_back(
64 std::make_unique<DeviceImageTy>(TgtBinDesc, TgtDeviceImage));
65 }
66
67 /// Return the device presented to the user as device \p DeviceNo if it is
68 /// initialized and ready. Otherwise return an error explaining the problem.
69 llvm::Expected<DeviceTy &> getDevice(uint32_t DeviceNo);
70
71 /// Iterate over all initialized and ready devices registered with this
72 /// plugin.
73 auto devices(ExclusiveDevicesAccessorTy &DevicesAccessor) {
74 return llvm::make_pointee_range(*DevicesAccessor);
75 }
76
77 /// Iterate over all device images registered with this plugin.
78 auto deviceImages() { return llvm::make_pointee_range(DeviceImages); }
79
80 /// Translation table retrieved from the binary
81 HostEntriesBeginToTransTableTy HostEntriesBeginToTransTable;
82 std::mutex TrlTblMtx; ///< For Translation Table
83 /// Host offload entries in order of image registration
84 llvm::SmallVector<llvm::offloading::EntryTy *>
85 HostEntriesBeginRegistrationOrder;
86
87 /// Map from ptrs on the host to an entry in the Translation Table
88 HostPtrToTableMapTy HostPtrToTableMap;
89 std::mutex TblMapMtx; ///< For HostPtrToTableMap
90
91 // Work around for plugins that call dlopen on shared libraries that call
92 // tgt_register_lib during their initialisation. Stash the pointers in a
93 // vector until the plugins are all initialised and then register them.
94 bool delayRegisterLib(__tgt_bin_desc *Desc) {
95 if (RTLsLoaded)
96 return false;
97 DelayedBinDesc.push_back(Desc);
98 return true;
99 }
100
101 void registerDelayedLibraries() {
102 // Only called by libomptarget constructor
103 RTLsLoaded = true;
104 for (auto *Desc : DelayedBinDesc)
105 __tgt_register_lib(Desc);
106 DelayedBinDesc.clear();
107 }
108
109 /// Return the number of usable devices.
110 int getNumDevices() { return getExclusiveDevicesAccessor()->size(); }
111
112 /// Return an exclusive handle to access the devices container.
113 ExclusiveDevicesAccessorTy getExclusiveDevicesAccessor() {
114 return Devices.getExclusiveAccessor();
115 }
116
117 /// Initialize \p Plugin. Returns true on success.
118 bool initializePlugin(GenericPluginTy &Plugin);
119
120 /// Initialize device \p DeviceNo of \p Plugin. Returns true on success.
121 bool initializeDevice(GenericPluginTy &Plugin, int32_t DeviceId);
122
123 /// Eagerly initialize all plugins and their devices.
124 void initializeAllDevices();
125
126 /// Iterator range for all plugins (in use or not, but always valid).
127 auto plugins() { return llvm::make_pointee_range(Plugins); }
128
129 /// Iterator range for all plugins (in use or not, but always valid).
130 auto plugins() const { return llvm::make_pointee_range(Plugins); }
131
132 /// Return the user provided requirements.
133 int64_t getRequirements() const { return Requirements.getRequirements(); }
134
135 /// Add \p Flags to the user provided requirements.
136 void addRequirements(int64_t Flags) { Requirements.addRequirements(Flags); }
137
138 /// Returns the number of plugins that are active.
139 int getNumActivePlugins() const {
140 int count = 0;
141 for (auto &R : plugins())
142 if (R.is_initialized())
143 ++count;
144
145 return count;
146 }
147
148private:
149 bool RTLsLoaded = false;
150 llvm::SmallVector<__tgt_bin_desc *> DelayedBinDesc;
151
152 // List of all plugins, in use or not.
153 llvm::SmallVector<std::unique_ptr<GenericPluginTy>> Plugins;
154
155 // Mapping of plugins to the OpenMP device identifier.
156 llvm::DenseMap<std::pair<const GenericPluginTy *, int32_t>, int32_t>
157 DeviceIds;
158
159 // Set of all device images currently in use.
160 llvm::DenseSet<const __tgt_device_image *> UsedImages;
161
162 /// Executable images and information extracted from the input images passed
163 /// to the runtime.
164 llvm::SmallVector<std::unique_ptr<DeviceImageTy>> DeviceImages;
165
166 /// The user provided requirements.
167 RequirementCollection Requirements;
168
169 std::mutex RTLsMtx; ///< For RTLs
170
171 /// Devices associated with plugins, accesses to the container are exclusive.
172 ProtectedObj<DeviceContainerTy> Devices;
173
174 /// References to upgraded legacy offloading entries.
175 std::list<llvm::SmallVector<llvm::offloading::EntryTy, 0>> LegacyEntries;
176 std::list<llvm::SmallVector<__tgt_device_image, 0>> LegacyImages;
177 llvm::DenseMap<__tgt_bin_desc *, __tgt_bin_desc> UpgradedDescriptors;
178 __tgt_bin_desc *upgradeLegacyEntries(__tgt_bin_desc *Desc);
179};
180
181/// Initialize the plugin manager and OpenMP runtime.
182void initRuntime();
183
184/// Deinitialize the plugin and delete it.
185void deinitRuntime();
186
187extern PluginManager *PM;
188
189#endif // OMPTARGET_PLUGIN_MANAGER_H
190

Warning: This file is not a C or C++ file. It does not have highlighting.

source code of offload/include/PluginManager.h