]> git.proxmox.com Git - ceph.git/blame - ceph/src/boost/boost/dll/import.hpp
update ceph source to reef 18.1.2
[ceph.git] / ceph / src / boost / boost / dll / import.hpp
CommitLineData
7c673cae 1// Copyright 2014 Renato Tegon Forti, Antony Polukhin.
1e59de90 2// Copyright Antony Polukhin, 2015-2022.
7c673cae
FG
3//
4// Distributed under the Boost Software License, Version 1.0.
5// (See accompanying file LICENSE_1_0.txt
6// or copy at http://www.boost.org/LICENSE_1_0.txt)
7
8#ifndef BOOST_DLL_IMPORT_HPP
9#define BOOST_DLL_IMPORT_HPP
10
92f5a8d4 11#include <boost/dll/config.hpp>
11fdf7f2
TL
12#include <boost/core/addressof.hpp>
13#include <boost/core/enable_if.hpp>
7c673cae
FG
14#include <boost/type_traits/is_object.hpp>
15#include <boost/make_shared.hpp>
16#include <boost/dll/shared_library.hpp>
7c673cae
FG
17#include <boost/move/move.hpp>
18
19#if defined(BOOST_NO_CXX11_TRAILING_RESULT_TYPES) || defined(BOOST_NO_CXX11_DECLTYPE) || defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || defined(BOOST_NO_CXX11_RVALUE_REFERENCES)
20# include <boost/function.hpp>
21#endif
22
23#ifdef BOOST_HAS_PRAGMA_ONCE
24# pragma once
25#endif
26
27/// \file boost/dll/import.hpp
28/// \brief Contains all the boost::dll::import* reference counting
29/// functions that hold a shared pointer to the instance of
30/// boost::dll::shared_library.
31
32namespace boost { namespace dll {
33
34
35namespace detail {
36
37 template <class T>
38 class library_function {
39 // Copying of `boost::dll::shared_library` is very expensive, so we use a `shared_ptr` to make it faster.
40 boost::shared_ptr<T> f_;
41
42 public:
43 inline library_function(const boost::shared_ptr<shared_library>& lib, T* func_ptr) BOOST_NOEXCEPT
44 : f_(lib, func_ptr)
45 {}
46
47#if defined(BOOST_NO_CXX11_TRAILING_RESULT_TYPES) || defined(BOOST_NO_CXX11_DECLTYPE) || defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || defined(BOOST_NO_CXX11_RVALUE_REFERENCES)
48 operator T*() const BOOST_NOEXCEPT {
49 return f_.get();
50 }
51#else
52
53 // Compilation error at this point means that imported function
54 // was called with unmatching parameters.
55 //
56 // Example:
1e59de90 57 // auto f = dll::import_symbol<void(int)>("function", "lib.so");
7c673cae
FG
58 // f("Hello"); // error: invalid conversion from 'const char*' to 'int'
59 // f(1, 2); // error: too many arguments to function
60 // f(); // error: too few arguments to function
61 template <class... Args>
62 inline auto operator()(Args&&... args) const
63 -> decltype( (*f_)(static_cast<Args&&>(args)...) )
64 {
65 return (*f_)(static_cast<Args&&>(args)...);
66 }
67#endif
68 };
69
70 template <class T, class = void>
71 struct import_type;
72
73 template <class T>
74 struct import_type<T, typename boost::disable_if<boost::is_object<T> >::type> {
75 typedef boost::dll::detail::library_function<T> base_type;
76
77#if defined(BOOST_NO_CXX11_TRAILING_RESULT_TYPES) || defined(BOOST_NO_CXX11_DECLTYPE) || defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || defined(BOOST_NO_CXX11_RVALUE_REFERENCES)
78 typedef boost::function<T> type;
79#else
80 typedef boost::dll::detail::library_function<T> type;
81#endif
82 };
83
84 template <class T>
85 struct import_type<T, typename boost::enable_if<boost::is_object<T> >::type> {
86 typedef boost::shared_ptr<T> base_type;
87 typedef boost::shared_ptr<T> type;
88 };
89} // namespace detail
90
91
92#ifndef BOOST_DLL_DOXYGEN
93# define BOOST_DLL_IMPORT_RESULT_TYPE inline typename boost::dll::detail::import_type<T>::type
94#endif
95
96
97/*!
98* Returns callable object or boost::shared_ptr<T> that holds the symbol imported
99* from the loaded library. Returned value refcounts usage
100* of the loaded shared library, so that it won't get unload until all copies of return value
101* are not destroyed.
102*
103* This call will succeed if call to \forcedlink{shared_library}`::has(const char* )`
104* function with the same symbol name returned `true`.
105*
106* For importing symbols by \b alias names use \forcedlink{import_alias} method.
107*
108* \b Examples:
109*
110* \code
1e59de90 111* boost::function<int(int)> f = import_symbol<int(int)>("test_lib.so", "integer_func_name");
7c673cae 112*
1e59de90 113* auto f_cpp11 = import_symbol<int(int)>("test_lib.so", "integer_func_name");
7c673cae
FG
114* \endcode
115*
116* \code
1e59de90 117* boost::shared_ptr<int> i = import_symbol<int>("test_lib.so", "integer_name");
7c673cae
FG
118* \endcode
119*
120* \b Template \b parameter \b T: Type of the symbol that we are going to import. Must be explicitly specified.
121*
122* \param lib Path to shared library or shared library to load function from.
123* \param name Null-terminated C or C++ mangled name of the function to import. Can handle std::string, char*, const char*.
124* \param mode An mode that will be used on library load.
125*
126* \return callable object if T is a function type, or boost::shared_ptr<T> if T is an object type.
127*
92f5a8d4 128* \throw \forcedlinkfs{system_error} if symbol does not exist or if the DLL/DSO was not loaded.
7c673cae
FG
129* Overload that accepts path also throws std::bad_alloc in case of insufficient memory.
130*/
131template <class T>
1e59de90 132BOOST_DLL_IMPORT_RESULT_TYPE import_symbol(const boost::dll::fs::path& lib, const char* name,
7c673cae
FG
133 load_mode::type mode = load_mode::default_mode)
134{
135 typedef typename boost::dll::detail::import_type<T>::base_type type;
136
137 boost::shared_ptr<boost::dll::shared_library> p = boost::make_shared<boost::dll::shared_library>(lib, mode);
138 return type(p, boost::addressof(p->get<T>(name)));
139}
140
1e59de90 141//! \overload boost::dll::import_symbol(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae 142template <class T>
1e59de90 143BOOST_DLL_IMPORT_RESULT_TYPE import_symbol(const boost::dll::fs::path& lib, const std::string& name,
7c673cae
FG
144 load_mode::type mode = load_mode::default_mode)
145{
1e59de90 146 return dll::import_symbol<T>(lib, name.c_str(), mode);
7c673cae
FG
147}
148
1e59de90 149//! \overload boost::dll::import_symbol(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae 150template <class T>
1e59de90 151BOOST_DLL_IMPORT_RESULT_TYPE import_symbol(const shared_library& lib, const char* name) {
7c673cae
FG
152 typedef typename boost::dll::detail::import_type<T>::base_type type;
153
154 boost::shared_ptr<boost::dll::shared_library> p = boost::make_shared<boost::dll::shared_library>(lib);
155 return type(p, boost::addressof(p->get<T>(name)));
156}
157
1e59de90 158//! \overload boost::dll::import_symbol(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae 159template <class T>
1e59de90
TL
160BOOST_DLL_IMPORT_RESULT_TYPE import_symbol(const shared_library& lib, const std::string& name) {
161 return dll::import_symbol<T>(lib, name.c_str());
7c673cae
FG
162}
163
1e59de90 164//! \overload boost::dll::import_symbol(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae 165template <class T>
1e59de90 166BOOST_DLL_IMPORT_RESULT_TYPE import_symbol(BOOST_RV_REF(shared_library) lib, const char* name) {
7c673cae
FG
167 typedef typename boost::dll::detail::import_type<T>::base_type type;
168
169 boost::shared_ptr<boost::dll::shared_library> p = boost::make_shared<boost::dll::shared_library>(
170 boost::move(lib)
171 );
172 return type(p, boost::addressof(p->get<T>(name)));
173}
174
1e59de90 175//! \overload boost::dll::import_symbol(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae 176template <class T>
1e59de90
TL
177BOOST_DLL_IMPORT_RESULT_TYPE import_symbol(BOOST_RV_REF(shared_library) lib, const std::string& name) {
178 return dll::import_symbol<T>(boost::move(lib), name.c_str());
7c673cae
FG
179}
180
181
182
183
184/*!
185* Returns callable object or boost::shared_ptr<T> that holds the symbol imported
186* from the loaded library. Returned value refcounts usage
187* of the loaded shared library, so that it won't get unload until all copies of return value
188* are not destroyed.
189*
190* This call will succeed if call to \forcedlink{shared_library}`::has(const char* )`
191* function with the same symbol name returned `true`.
192*
193* For importing symbols by \b non \b alias names use \forcedlink{import} method.
194*
195* \b Examples:
196*
197* \code
198* boost::function<int(int)> f = import_alias<int(int)>("test_lib.so", "integer_func_alias_name");
199*
200* auto f_cpp11 = import_alias<int(int)>("test_lib.so", "integer_func_alias_name");
201* \endcode
202*
203* \code
204* boost::shared_ptr<int> i = import_alias<int>("test_lib.so", "integer_alias_name");
205* \endcode
206*
207* \code
208* \endcode
209*
210* \b Template \b parameter \b T: Type of the symbol alias that we are going to import. Must be explicitly specified.
211*
212* \param lib Path to shared library or shared library to load function from.
213* \param name Null-terminated C or C++ mangled name of the function or variable to import. Can handle std::string, char*, const char*.
214* \param mode An mode that will be used on library load.
215*
216* \return callable object if T is a function type, or boost::shared_ptr<T> if T is an object type.
217*
92f5a8d4 218* \throw \forcedlinkfs{system_error} if symbol does not exist or if the DLL/DSO was not loaded.
7c673cae
FG
219* Overload that accepts path also throws std::bad_alloc in case of insufficient memory.
220*/
221template <class T>
92f5a8d4 222BOOST_DLL_IMPORT_RESULT_TYPE import_alias(const boost::dll::fs::path& lib, const char* name,
7c673cae
FG
223 load_mode::type mode = load_mode::default_mode)
224{
225 typedef typename boost::dll::detail::import_type<T>::base_type type;
226
227 boost::shared_ptr<boost::dll::shared_library> p = boost::make_shared<boost::dll::shared_library>(lib, mode);
228 return type(p, p->get<T*>(name));
229}
230
92f5a8d4 231//! \overload boost::dll::import_alias(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae 232template <class T>
92f5a8d4 233BOOST_DLL_IMPORT_RESULT_TYPE import_alias(const boost::dll::fs::path& lib, const std::string& name,
7c673cae
FG
234 load_mode::type mode = load_mode::default_mode)
235{
1e59de90 236 return dll::import_alias<T>(lib, name.c_str(), mode);
7c673cae
FG
237}
238
92f5a8d4 239//! \overload boost::dll::import_alias(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae
FG
240template <class T>
241BOOST_DLL_IMPORT_RESULT_TYPE import_alias(const shared_library& lib, const char* name) {
242 typedef typename boost::dll::detail::import_type<T>::base_type type;
243
244 boost::shared_ptr<boost::dll::shared_library> p = boost::make_shared<boost::dll::shared_library>(lib);
245 return type(p, p->get<T*>(name));
246}
247
92f5a8d4 248//! \overload boost::dll::import_alias(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae
FG
249template <class T>
250BOOST_DLL_IMPORT_RESULT_TYPE import_alias(const shared_library& lib, const std::string& name) {
1e59de90 251 return dll::import_alias<T>(lib, name.c_str());
7c673cae
FG
252}
253
92f5a8d4 254//! \overload boost::dll::import_alias(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae
FG
255template <class T>
256BOOST_DLL_IMPORT_RESULT_TYPE import_alias(BOOST_RV_REF(shared_library) lib, const char* name) {
257 typedef typename boost::dll::detail::import_type<T>::base_type type;
258
259 boost::shared_ptr<boost::dll::shared_library> p = boost::make_shared<boost::dll::shared_library>(
260 boost::move(lib)
261 );
262 return type(p, p->get<T*>(name));
263}
264
92f5a8d4 265//! \overload boost::dll::import_alias(const boost::dll::fs::path& lib, const char* name, load_mode::type mode)
7c673cae
FG
266template <class T>
267BOOST_DLL_IMPORT_RESULT_TYPE import_alias(BOOST_RV_REF(shared_library) lib, const std::string& name) {
1e59de90 268 return dll::import_alias<T>(boost::move(lib), name.c_str());
7c673cae
FG
269}
270
271#undef BOOST_DLL_IMPORT_RESULT_TYPE
272
273
274}} // boost::dll
275
276#endif // BOOST_DLL_IMPORT_HPP
277