| 137 | |
| 138 | static void buildXRayProfileMap() __attribute__((xray_never_instrument)); |
| 139 | static void buildXRayProfileMap() |
| 140 | { |
| 141 | std::call_once(g_xray_map_once, [] |
| 142 | { |
| 143 | const int32_t max_id = __xray_max_function_id(); |
| 144 | if (max_id <= 0) return; |
| 145 | g_xray_max_id = max_id; |
| 146 | |
| 147 | /// Build NameRef → profile_data_index map first. |
| 148 | const LLVMProfileData * begin = __llvm_profile_begin_data(); // NOLINT |
| 149 | const LLVMProfileData * end = __llvm_profile_end_data(); // NOLINT |
| 150 | const uint32_t n = static_cast<uint32_t>(end - begin); |
| 151 | std::unordered_map<uint64_t, uint32_t> name_hash_to_idx; |
| 152 | name_hash_to_idx.reserve(n); |
| 153 | for (uint32_t i = 0; i < n; ++i) |
| 154 | name_hash_to_idx.emplace(begin[i].NameRef, i); |
| 155 | |
| 156 | /// Allocate depth array. |
| 157 | g_xray_depth_size = n; |
| 158 | g_xray_min_depth = new std::atomic<uint32_t>[n]; // NOLINT |
| 159 | for (uint32_t i = 0; i < n; ++i) |
| 160 | g_xray_min_depth[i].store(UINT32_MAX, std::memory_order_relaxed); |
| 161 | |
| 162 | /// For each XRay function_id, resolve to profile_data_index via symbol name hash. |
| 163 | g_xray_to_profile = new uint32_t[static_cast<size_t>(max_id) + 1]; // NOLINT |
| 164 | std::fill(g_xray_to_profile, g_xray_to_profile + max_id + 1, UINT32_MAX); |
| 165 | |
| 166 | for (int32_t id = 1; id <= max_id; ++id) |
| 167 | { |
| 168 | const void * addr = reinterpret_cast<const void *>(__xray_function_address(id)); |
| 169 | if (!addr) continue; |
| 170 | Dl_info info; |
| 171 | if (!dladdr(addr, &info) || !info.dli_sname) continue; |
| 172 | const uint64_t h = fnv64(info.dli_sname); |
| 173 | const auto it = name_hash_to_idx.find(h); |
| 174 | if (it != name_hash_to_idx.end()) |
| 175 | g_xray_to_profile[id] = it->second; |
| 176 | } |
| 177 | }); |
| 178 | } |
| 179 | |
| 180 | static void xrayHandler(int32_t func_id, XRayEntryType type) __attribute__((xray_never_instrument)); |
| 181 | static void xrayHandler(int32_t func_id, XRayEntryType type) |