diff options
author | vvvv <vvvv@ydb.tech> | 2024-02-06 20:01:22 +0300 |
---|---|---|
committer | vvvv <vvvv@ydb.tech> | 2024-02-06 20:22:16 +0300 |
commit | 0203b7a9a40828bb2bd4c32029b79ff0ea3d1f8f (patch) | |
tree | e630d0d5bd0bd29fc8c2d2842ed2cfde781b993a /contrib/libs/llvm16/tools/llvm-xray/xray-extract.cpp | |
parent | ba27db76d99d12a4f1c06960b5449423218614c4 (diff) | |
download | ydb-0203b7a9a40828bb2bd4c32029b79ff0ea3d1f8f.tar.gz |
llvm16 targets
Diffstat (limited to 'contrib/libs/llvm16/tools/llvm-xray/xray-extract.cpp')
-rw-r--r-- | contrib/libs/llvm16/tools/llvm-xray/xray-extract.cpp | 101 |
1 files changed, 101 insertions, 0 deletions
diff --git a/contrib/libs/llvm16/tools/llvm-xray/xray-extract.cpp b/contrib/libs/llvm16/tools/llvm-xray/xray-extract.cpp new file mode 100644 index 0000000000..52767a00f6 --- /dev/null +++ b/contrib/libs/llvm16/tools/llvm-xray/xray-extract.cpp @@ -0,0 +1,101 @@ +//===- xray-extract.cpp: XRay Instrumentation Map Extraction --------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// Implementation of the xray-extract.h interface. +// +// FIXME: Support other XRay-instrumented binary formats other than ELF. +// +//===----------------------------------------------------------------------===// + + +#include "func-id-helper.h" +#include "xray-registry.h" +#include "llvm/Object/ObjectFile.h" +#include "llvm/Support/CommandLine.h" +#include "llvm/Support/Error.h" +#include "llvm/Support/FileSystem.h" +#include "llvm/Support/Format.h" +#include "llvm/Support/raw_ostream.h" +#include "llvm/XRay/InstrumentationMap.h" + +using namespace llvm; +using namespace llvm::xray; +using namespace llvm::yaml; + +// llvm-xray extract +// ---------------------------------------------------------------------------- +static cl::SubCommand Extract("extract", "Extract instrumentation maps"); +static cl::opt<std::string> ExtractInput(cl::Positional, + cl::desc("<input file>"), cl::Required, + cl::sub(Extract)); +static cl::opt<std::string> + ExtractOutput("output", cl::value_desc("output file"), cl::init("-"), + cl::desc("output file; use '-' for stdout"), + cl::sub(Extract)); +static cl::alias ExtractOutput2("o", cl::aliasopt(ExtractOutput), + cl::desc("Alias for -output")); +static cl::opt<bool> ExtractSymbolize("symbolize", cl::value_desc("symbolize"), + cl::init(false), + cl::desc("symbolize functions"), + cl::sub(Extract)); +static cl::alias ExtractSymbolize2("s", cl::aliasopt(ExtractSymbolize), + cl::desc("alias for -symbolize")); +static cl::opt<bool> Demangle("demangle", + cl::desc("demangle symbols (default)"), + cl::sub(Extract)); +static cl::opt<bool> NoDemangle("no-demangle", + cl::desc("don't demangle symbols"), + cl::sub(Extract)); + +namespace { + +void exportAsYAML(const InstrumentationMap &Map, raw_ostream &OS, + FuncIdConversionHelper &FH) { + // First we translate the sleds into the YAMLXRaySledEntry objects in a deque. + std::vector<YAMLXRaySledEntry> YAMLSleds; + auto Sleds = Map.sleds(); + YAMLSleds.reserve(std::distance(Sleds.begin(), Sleds.end())); + for (const auto &Sled : Sleds) { + auto FuncId = Map.getFunctionId(Sled.Function); + if (!FuncId) + return; + YAMLSleds.push_back( + {*FuncId, Sled.Address, Sled.Function, Sled.Kind, Sled.AlwaysInstrument, + ExtractSymbolize ? FH.SymbolOrNumber(*FuncId) : "", Sled.Version}); + } + Output Out(OS, nullptr, 0); + Out << YAMLSleds; +} + +} // namespace + +static CommandRegistration Unused(&Extract, []() -> Error { + auto InstrumentationMapOrError = loadInstrumentationMap(ExtractInput); + if (!InstrumentationMapOrError) + return joinErrors(make_error<StringError>( + Twine("Cannot extract instrumentation map from '") + + ExtractInput + "'.", + std::make_error_code(std::errc::invalid_argument)), + InstrumentationMapOrError.takeError()); + + std::error_code EC; + raw_fd_ostream OS(ExtractOutput, EC, sys::fs::OpenFlags::OF_TextWithCRLF); + if (EC) + return make_error<StringError>( + Twine("Cannot open file '") + ExtractOutput + "' for writing.", EC); + const auto &FunctionAddresses = + InstrumentationMapOrError->getFunctionAddresses(); + symbolize::LLVMSymbolizer::Options opts; + if (Demangle.getPosition() < NoDemangle.getPosition()) + opts.Demangle = false; + symbolize::LLVMSymbolizer Symbolizer(opts); + llvm::xray::FuncIdConversionHelper FuncIdHelper(ExtractInput, Symbolizer, + FunctionAddresses); + exportAsYAML(*InstrumentationMapOrError, OS, FuncIdHelper); + return Error::success(); +}); |