1//===- InstrumentationMap.h - XRay Instrumentation Map ----------*- 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// Defines the interface for extracting the instrumentation map from an
10// XRay-instrumented binary.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_XRAY_INSTRUMENTATIONMAP_H
15#define LLVM_XRAY_INSTRUMENTATIONMAP_H
16
17#include "llvm/ADT/StringRef.h"
18#include "llvm/Support/Error.h"
19#include "llvm/Support/YAMLTraits.h"
20#include <cstdint>
21#include <optional>
22#include <unordered_map>
23#include <vector>
24
25namespace llvm {
26
27namespace xray {
28
29// Forward declare to make a friend.
30class InstrumentationMap;
31
32/// Loads the instrumentation map from |Filename|. This auto-deduces the type of
33/// the instrumentation map.
34Expected<InstrumentationMap> loadInstrumentationMap(StringRef Filename);
35
36/// Represents an XRay instrumentation sled entry from an object file.
37struct SledEntry {
38 /// Each entry here represents the kinds of supported instrumentation map
39 /// entries.
40 enum class FunctionKinds { ENTRY, EXIT, TAIL, LOG_ARGS_ENTER, CUSTOM_EVENT };
41
42 /// The address of the sled.
43 uint64_t Address;
44
45 /// The address of the function.
46 uint64_t Function;
47
48 /// The kind of sled.
49 FunctionKinds Kind;
50
51 /// Whether the sled was annotated to always be instrumented.
52 bool AlwaysInstrument;
53
54 unsigned char Version;
55};
56
57struct YAMLXRaySledEntry {
58 int32_t FuncId;
59 yaml::Hex64 Address;
60 yaml::Hex64 Function;
61 SledEntry::FunctionKinds Kind;
62 bool AlwaysInstrument;
63 std::string FunctionName;
64 unsigned char Version;
65};
66
67/// The InstrumentationMap represents the computed function id's and indicated
68/// function addresses from an object file (or a YAML file). This provides an
69/// interface to just the mapping between the function id, and the function
70/// address.
71///
72/// We also provide raw access to the actual instrumentation map entries we find
73/// associated with a particular object file.
74///
75class InstrumentationMap {
76public:
77 using FunctionAddressMap = std::unordered_map<int32_t, uint64_t>;
78 using FunctionAddressReverseMap = std::unordered_map<uint64_t, int32_t>;
79 using SledContainer = std::vector<SledEntry>;
80
81private:
82 SledContainer Sleds;
83 FunctionAddressMap FunctionAddresses;
84 FunctionAddressReverseMap FunctionIds;
85
86 friend Expected<InstrumentationMap> loadInstrumentationMap(StringRef);
87
88public:
89 /// Provides a raw accessor to the unordered map of function addresses.
90 const FunctionAddressMap &getFunctionAddresses() { return FunctionAddresses; }
91
92 /// Returns an XRay computed function id, provided a function address.
93 std::optional<int32_t> getFunctionId(uint64_t Addr) const;
94
95 /// Returns the function address for a function id.
96 std::optional<uint64_t> getFunctionAddr(int32_t FuncId) const;
97
98 /// Provide read-only access to the entries of the instrumentation map.
99 const SledContainer &sleds() const { return Sleds; };
100};
101
102} // end namespace xray
103
104namespace yaml {
105
106template <> struct ScalarEnumerationTraits<xray::SledEntry::FunctionKinds> {
107 static void enumeration(IO &IO, xray::SledEntry::FunctionKinds &Kind) {
108 IO.enumCase(Val&: Kind, Str: "function-enter", ConstVal: xray::SledEntry::FunctionKinds::ENTRY);
109 IO.enumCase(Val&: Kind, Str: "function-exit", ConstVal: xray::SledEntry::FunctionKinds::EXIT);
110 IO.enumCase(Val&: Kind, Str: "tail-exit", ConstVal: xray::SledEntry::FunctionKinds::TAIL);
111 IO.enumCase(Val&: Kind, Str: "log-args-enter",
112 ConstVal: xray::SledEntry::FunctionKinds::LOG_ARGS_ENTER);
113 IO.enumCase(Val&: Kind, Str: "custom-event",
114 ConstVal: xray::SledEntry::FunctionKinds::CUSTOM_EVENT);
115 }
116};
117
118template <> struct MappingTraits<xray::YAMLXRaySledEntry> {
119 static void mapping(IO &IO, xray::YAMLXRaySledEntry &Entry) {
120 IO.mapRequired(Key: "id", Val&: Entry.FuncId);
121 IO.mapRequired(Key: "address", Val&: Entry.Address);
122 IO.mapRequired(Key: "function", Val&: Entry.Function);
123 IO.mapRequired(Key: "kind", Val&: Entry.Kind);
124 IO.mapRequired(Key: "always-instrument", Val&: Entry.AlwaysInstrument);
125 IO.mapOptional(Key: "function-name", Val&: Entry.FunctionName);
126 IO.mapOptional(Key: "version", Val&: Entry.Version, Default: 0);
127 }
128
129 static constexpr bool flow = true;
130};
131
132} // end namespace yaml
133
134} // end namespace llvm
135
136LLVM_YAML_IS_SEQUENCE_VECTOR(xray::YAMLXRaySledEntry)
137
138#endif // LLVM_XRAY_INSTRUMENTATIONMAP_H
139

source code of llvm/include/llvm/XRay/InstrumentationMap.h