File indexing completed on 2025-01-18 09:30:43
0001
0002
0003
0004
0005
0006
0007
0008 #ifndef BOOST_DLL_DETAIL_POSIX_PATH_FROM_HANDLE_HPP
0009 #define BOOST_DLL_DETAIL_POSIX_PATH_FROM_HANDLE_HPP
0010
0011 #include <boost/dll/config.hpp>
0012 #include <boost/dll/detail/system_error.hpp>
0013 #include <boost/dll/detail/posix/program_location_impl.hpp>
0014 #include <boost/predef/os.h>
0015
0016 #ifdef BOOST_HAS_PRAGMA_ONCE
0017 # pragma once
0018 #endif
0019
0020 #if BOOST_OS_MACOS || BOOST_OS_IOS
0021
0022 # include <mach-o/dyld.h>
0023 # include <mach-o/nlist.h>
0024 # include <cstddef> // for std::ptrdiff_t
0025
0026 namespace boost { namespace dll { namespace detail {
0027 inline void* strip_handle(void* handle) BOOST_NOEXCEPT {
0028 return reinterpret_cast<void*>(
0029 (reinterpret_cast<std::ptrdiff_t>(handle) >> 2) << 2
0030 );
0031 }
0032
0033 inline boost::dll::fs::path path_from_handle(void* handle, boost::dll::fs::error_code &ec) {
0034 handle = strip_handle(handle);
0035
0036
0037
0038 const uint32_t count = _dyld_image_count();
0039 for (uint32_t i = 0; i <= count; ++i) {
0040
0041
0042 const char* image_name = _dyld_get_image_name(i);
0043
0044
0045 void* probe_handle = dlopen(image_name, RTLD_LAZY);
0046 dlclose(probe_handle);
0047
0048
0049 if (handle == strip_handle(probe_handle)) {
0050 boost::dll::detail::reset_dlerror();
0051 return image_name;
0052 }
0053 }
0054
0055 boost::dll::detail::reset_dlerror();
0056 ec = boost::dll::fs::make_error_code(
0057 boost::dll::fs::errc::bad_file_descriptor
0058 );
0059
0060 return boost::dll::fs::path();
0061 }
0062
0063 }}}
0064
0065 #elif BOOST_OS_ANDROID
0066
0067 #include <boost/dll/runtime_symbol_info.hpp>
0068
0069 namespace boost { namespace dll { namespace detail {
0070
0071 struct soinfo {
0072
0073
0074 const void* phdr;
0075 size_t phnum;
0076 void* entry;
0077 void* base;
0078
0079 };
0080
0081 inline boost::dll::fs::path path_from_handle(const void* handle, boost::dll::fs::error_code &ec) {
0082 static const std::size_t work_around_b_24465209__offset = 128;
0083 const struct soinfo* si = reinterpret_cast<const struct soinfo*>(
0084 static_cast<const char*>(handle) + work_around_b_24465209__offset
0085 );
0086 boost::dll::fs::path ret = boost::dll::symbol_location_ptr(si->base, ec);
0087
0088 if (ec) {
0089 ec.clear();
0090 si = static_cast<const struct soinfo*>(handle);
0091 return boost::dll::symbol_location_ptr(si->base, ec);
0092 }
0093
0094 return ret;
0095 }
0096
0097 }}}
0098
0099 #else
0100
0101
0102 #include <dlfcn.h>
0103
0104 #if BOOST_OS_QNX
0105
0106 # include <sys/link.h>
0107 #else
0108 # include <link.h> // struct link_map
0109 #endif
0110
0111 namespace boost { namespace dll { namespace detail {
0112
0113 #if BOOST_OS_QNX
0114
0115 struct link_map {
0116 void *l_addr;
0117 char *l_name;
0118
0119 };
0120 #endif
0121
0122 inline boost::dll::fs::path path_from_handle(void* handle, boost::dll::fs::error_code &ec) {
0123
0124
0125
0126
0127
0128
0129
0130
0131
0132
0133
0134
0135 const struct link_map* link_map = 0;
0136 #if BOOST_OS_BSD_FREE
0137
0138
0139 if (dlinfo(handle, RTLD_DI_LINKMAP, &link_map) < 0) {
0140 link_map = 0;
0141 }
0142 #else
0143 link_map = static_cast<const struct link_map*>(handle);
0144 #endif
0145 if (!link_map) {
0146 boost::dll::detail::reset_dlerror();
0147 ec = boost::dll::fs::make_error_code(
0148 boost::dll::fs::errc::bad_file_descriptor
0149 );
0150
0151 return boost::dll::fs::path();
0152 }
0153
0154 if (!link_map->l_name || *link_map->l_name == '\0') {
0155 return program_location_impl(ec);
0156 }
0157
0158 return boost::dll::fs::path(link_map->l_name);
0159 }
0160
0161 }}}
0162
0163 #endif
0164
0165 #endif
0166
0167