mirror of
https://github.com/revng/revng
synced 2026-06-21 14:07:57 +00:00
440 lines
13 KiB
C++
440 lines
13 KiB
C++
#pragma once
|
|
|
|
//
|
|
// This file is distributed under the MIT License. See LICENSE.md for details.
|
|
//
|
|
|
|
#include "revng/Model/Binary.h"
|
|
#include "revng/Pipeline/Rank.h"
|
|
#include "revng/Support/BasicBlockID/YAMLTraits.h"
|
|
#include "revng/Support/MetaAddress.h"
|
|
#include "revng/Support/YAMLTraits.h"
|
|
|
|
namespace revng::ranks {
|
|
|
|
namespace detail {
|
|
|
|
using TDK = model::TypeDefinition::Key;
|
|
using SFK = model::StructField::Key;
|
|
using UFK = model::UnionField::Key;
|
|
using CAK = model::Argument::Key;
|
|
using NRK = model::NamedTypedRegister::Key;
|
|
|
|
} // namespace detail
|
|
|
|
static_assert(HasScalarOrEnumTraits<MetaAddress>);
|
|
static_assert(HasScalarOrEnumTraits<BasicBlockID>);
|
|
|
|
using pipeline::defineRank;
|
|
|
|
/// \defgroup Root rank
|
|
/// @{
|
|
|
|
/// This is the root rank, as such it has no key (there can only be one).
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /binary
|
|
/// ```
|
|
inline auto Binary = pipeline::defineRootRank<"binary">();
|
|
|
|
/// @}
|
|
/// \defgroup Generic ranks
|
|
/// @{
|
|
|
|
/// This is the rank for *isolated* functions.
|
|
///
|
|
/// The key is the model key of the function (entry point address).
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /function/0x1000:Code_aarch64
|
|
/// ```
|
|
inline auto Function = defineRank<"function", // formatting
|
|
model::Function::Key,
|
|
"Functions">(Binary);
|
|
|
|
/// This is the rank for representing an imported *dynamic* function.
|
|
///
|
|
/// The key is the model key (its name).
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /dynamic-function/printf
|
|
/// ```
|
|
inline auto DynamicFunction = defineRank<"dynamic-function",
|
|
model::DynamicFunction::Key,
|
|
"ImportedDynamicFunctions">(Binary);
|
|
|
|
/// This is the rank for representing a binary segment.
|
|
///
|
|
/// The key is the model key (its start address + virtual size).
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /segment/0x1000:Code_aarch64-256
|
|
/// ```
|
|
inline auto Segment = defineRank<"segment", // formatting
|
|
model::Segment::Key,
|
|
"Segments">(Binary);
|
|
|
|
/// This is the rank for representing comments in isolated function *bodies*.
|
|
///
|
|
/// The key is the index of the comment within its function
|
|
/// (based on the emission order)
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /statement-comment/0x1000:Code_aarch64/0
|
|
/// /statement-comment/0x1024:Code_aarch64/1
|
|
/// /statement-comment/0x1144:Code_aarch64/2
|
|
/// ```
|
|
inline auto StatementComment = defineRank<"statement-comment", // formatting
|
|
uint64_t>(Function);
|
|
|
|
/// @}
|
|
/// \defgroup Type system related ranks
|
|
/// @{
|
|
|
|
/// This is the rank for a type definition.
|
|
///
|
|
/// The key is the model key of the definition (its unique numeric ID and kind).
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /type-definition/0-StructDefinition
|
|
/// /type-definition/1-UnionDefinition
|
|
/// /type-definition/2-EnumDefinition
|
|
/// ```
|
|
inline auto TypeDefinition = defineRank<"type-definition",
|
|
detail::TDK,
|
|
"TypeDefinitions">(Binary);
|
|
|
|
/// This is the rank for a struct field.
|
|
///
|
|
/// The key is the model key of the definition (offset from the beginning of
|
|
/// the struct).
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /struct-field/3-StructDefinition/4
|
|
/// /struct-field/4-StructDefinition/16
|
|
/// ```
|
|
inline auto StructField = defineRank<"struct-field",
|
|
detail::SFK,
|
|
"Fields">(TypeDefinition);
|
|
|
|
/// This is the rank for a union field.
|
|
///
|
|
/// The key is the model key of the definition (numeric index within the union).
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /union-field/5-UnionDefinition/0
|
|
/// /union-field/6-UnionDefinition/1
|
|
/// ```
|
|
inline auto UnionField = defineRank<"union-field", // formatting
|
|
detail::UFK,
|
|
"Fields">(TypeDefinition);
|
|
|
|
/// This is the rank for an enumeration entry.
|
|
///
|
|
/// The key is the model key of the definition (its numeric value).
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /enum-entry/7-EnumDefinition/1
|
|
/// /enum-entry/8-EnumDefinition/42
|
|
/// /enum-entry/9-EnumDefinition/18446744073709551615
|
|
/// ```
|
|
inline auto EnumEntry = defineRank<"enum-entry",
|
|
model::EnumEntry::Key,
|
|
"Entries">(TypeDefinition);
|
|
|
|
/// This is the rank for representing a primitive type.
|
|
///
|
|
/// The key is the *serialized* name of the primitive.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /primitive/void
|
|
/// /primitive/int64_t
|
|
/// /primitive/number64_t
|
|
/// /primitive/pointer_or_number64_t
|
|
/// ```
|
|
inline auto PrimitiveType = defineRank<"primitive", std::string>(Binary);
|
|
|
|
/// This is the rank for a *C ABI* function argument.
|
|
///
|
|
/// The key is the model key of the definition (its index in the prototype).
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /cabi-argument/10-CABIFunctionDefinition/0
|
|
/// /cabi-argument/11-CABIFunctionDefinition/1
|
|
/// /cabi-argument/12-CABIFunctionDefinition/2
|
|
/// ```
|
|
inline auto CABIArgument = defineRank<"cabi-argument",
|
|
detail::CAK,
|
|
"Arguments">(TypeDefinition);
|
|
|
|
/// This is the rank for the return value of a *C ABI* function.
|
|
///
|
|
/// The key is the model key of the prototype.
|
|
///
|
|
/// Note that this is *not* a subrank of the prototype.
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /return-value/22-CABIFunctionDefinition
|
|
/// ```
|
|
inline auto ReturnValue = defineRank<"return-value", detail::TDK>(Binary);
|
|
|
|
/// This is the rank for a *raw* function argument.
|
|
///
|
|
/// The key is the model key of the definition (register used by this argument).
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /raw-argument/13-RawFunctionDefinition/rdi_x86_64
|
|
/// /raw-argument/14-RawFunctionDefinition/x3_aarch64
|
|
/// /raw-argument/15-RawFunctionDefinition/r3_s390x
|
|
/// ```
|
|
inline auto RawArgument = defineRank<"raw-argument",
|
|
detail::NRK,
|
|
"Arguments">(TypeDefinition);
|
|
|
|
/// This is the rank for *all of* stack arguments of a *raw* function.
|
|
///
|
|
/// The key is the model key of the prototype.
|
|
///
|
|
/// Note that this is *not* a subrank of the prototype.
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /raw-stack-arguments/21-RawFunctionDefinition
|
|
/// ```
|
|
inline auto RawStackArguments = defineRank<"raw-stack-arguments",
|
|
detail::TDK,
|
|
"StackArgumentsType">(Binary);
|
|
|
|
/// This is the rank for the return value of a *C ABI* function.
|
|
///
|
|
/// The key is the model key of the prototype.
|
|
///
|
|
/// Note that this is *not* a subrank of the prototype.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /return-register/18-RawFunctionDefinition/rax_x86_64
|
|
/// /return-register/19-RawFunctionDefinition/x2_aarch64
|
|
/// /return-register/20-RawFunctionDefinition/r2_s390x
|
|
/// ```
|
|
inline auto ReturnRegister = defineRank<"return-register",
|
|
detail::NRK,
|
|
"ReturnValues">(TypeDefinition);
|
|
|
|
/// @}
|
|
/// \defgroup Raw byte view only ranks
|
|
/// @{
|
|
|
|
/// This is the rank for representing an arbitrary byte within the binary.
|
|
///
|
|
/// The key is the address of the byte.
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /raw-byte/0x1000:Code_aarch64
|
|
/// ```
|
|
inline auto RawByte = defineRank<"raw-byte", MetaAddress>(Binary);
|
|
|
|
/// This is the rank for representing an arbitrary sequence of bytes within
|
|
/// the binary.
|
|
///
|
|
/// The key is the address of the *last* byte in the sequence.
|
|
/// The *first* byte is encoded in the parent `RawByte`'s key.
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /raw-byte-range/0x1000:Code_aarch64/0x1008:Code_aarch64
|
|
/// ```
|
|
inline auto RawByteRange = defineRank<"raw-byte-range", MetaAddress>(RawByte);
|
|
|
|
/// @}
|
|
/// \defgroup Assembly view only ranks
|
|
/// @{
|
|
|
|
/// This is the rank for a basic block of an *isolated* function.
|
|
///
|
|
/// The key is the basic block ID (its entry address + a deduplication index).
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /basic-block/0x1000:Code_aarch64/0x1004:Code_aarch64
|
|
/// /basic-block/0x1000:Code_aarch64/0x1004:Code_aarch64-1
|
|
/// /basic-block/0x1000:Code_aarch64/0x1004:Code_aarch64-2
|
|
/// ```
|
|
inline auto BasicBlock = defineRank<"basic-block", BasicBlockID>(Function);
|
|
|
|
/// This is the rank for an instruction within an *isolated* function.
|
|
///
|
|
/// The key is the address of the instruction.
|
|
///
|
|
/// Note that the same instruction is considered two distinct instructions
|
|
/// when it's a part of separate (potentially inlined) basic blocks.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /instruction/0x1000:Code_aarch64/0x1004:Code_aarch64/0x1008:Code_aarch64
|
|
/// /instruction/0x1000:Code_aarch64/0x1004:Code_aarch64-1/0x1008:Code_aarch64
|
|
/// /instruction/0x1000:Code_aarch64/0x1004:Code_aarch64-2/0x1008:Code_aarch64
|
|
/// ```
|
|
inline auto Instruction = defineRank<"instruction", MetaAddress>(BasicBlock);
|
|
|
|
/// @}
|
|
/// \defgroup Decompiled view only ranks
|
|
/// @{
|
|
|
|
/// This is the rank for representing *local* variables.
|
|
///
|
|
/// The key is the index of the variable within its function
|
|
/// (based on the emission order)
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /local-variable/0x1000:Code_aarch64/0
|
|
/// /local-variable/0x1024:Code_aarch64/1
|
|
/// /local-variable/0x1144:Code_aarch64/2
|
|
/// ```
|
|
inline auto LocalVariable = defineRank<"local-variable", uint64_t>(Function);
|
|
|
|
/// This is the rank for the local stack frame variable.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /stack-frame-variable/0x1000:Code_aarch64
|
|
/// ```
|
|
inline auto StackFrameVariable = defineRank<"stack-frame-variable",
|
|
model::Function::Key>(Binary);
|
|
|
|
/// This is the rank for representing *local* variables with *reserved* names.
|
|
///
|
|
/// The key is the name of the variable.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /reserved-local-variable/0x1000:Code_aarch64/stack
|
|
/// /reserved-local-variable/0x1024:Code_aarch64/stack
|
|
/// ```
|
|
inline auto ReservedLocalVariable = defineRank<"reserved-local-variable",
|
|
std::string>(Function);
|
|
|
|
/// This is the rank for representing goto labels.
|
|
///
|
|
/// The key is the index of the label within its function
|
|
/// (based on the emission order)
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /goto-label/0x1000:Code_aarch64/0
|
|
/// /goto-label/0x1024:Code_aarch64/1
|
|
/// /goto-label/0x1144:Code_aarch64/2
|
|
/// ```
|
|
inline auto GotoLabel = defineRank<"goto-label", uint64_t>(Function);
|
|
|
|
/// This is the rank for representing *structs* returned by *raw* function
|
|
/// prototypes (they return a set of registers - so these structs are
|
|
/// artificially created to represent said registers as fields).
|
|
///
|
|
/// The key is the model key of the prototype.
|
|
///
|
|
/// Note that this is *not* a subrank of the prototype.
|
|
///
|
|
/// Example:
|
|
/// ```
|
|
/// /artificial-struct/23-RawFunctionDefinition
|
|
/// ```
|
|
inline auto ArtificialStruct = defineRank<"artificial-struct",
|
|
model::TypeDefinition::Key>(Binary);
|
|
|
|
/// This is the rank for representing *arguments* of imported dynamic functions.
|
|
///
|
|
/// The key is the name of the argument.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /dynamic-function-argument/pow/base
|
|
/// /dynamic-function-argument/pow/exp
|
|
/// /dynamic-function-argument/printf/format
|
|
/// ```
|
|
inline auto DynamicFunctionArgument = defineRank<"dynamic-function-argument",
|
|
std::string>(DynamicFunction);
|
|
|
|
/// This is the rank for representing QEMU and LLVM helper functions.
|
|
///
|
|
/// The key is the name of the helper.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /helper-function/helper_clz64
|
|
/// /helper-function/helper_qsub16
|
|
/// /helper-function/aarch64_save_sp
|
|
/// /helper-function/qemu_strnlen
|
|
/// ```
|
|
inline auto HelperFunction = defineRank<"helper-function", std::string>(Binary);
|
|
|
|
/// This is the rank for representing *struct* return value types of
|
|
/// QEMU and LLVM helper functions.
|
|
///
|
|
/// The key is the name of the helper.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /helper-struct-type/helper_clz64
|
|
/// /helper-struct-type/helper_qsub16
|
|
/// /helper-struct-type/aarch64_save_sp
|
|
/// /helper-struct-type/qemu_strnlen
|
|
/// ```
|
|
inline auto HelperStructType = defineRank<"helper-struct-type", // formatting
|
|
std::string>(Binary);
|
|
|
|
/// This is the rank for representing *fields* or struct return value types of
|
|
/// QEMU and LLVM helper functions.
|
|
///
|
|
/// The key is the name of the field.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /helper-struct-field/helper_clz64/field_0
|
|
/// /helper-struct-field/helper_qsub16/field_1
|
|
/// /helper-struct-field/aarch64_save_sp/field_2
|
|
/// /helper-struct-field/qemu_strnlen/field_3
|
|
/// ```
|
|
// TODO: consider using indexes instead.
|
|
inline auto HelperStructField = defineRank<"helper-struct-field",
|
|
std::string>(HelperStructType);
|
|
|
|
/// This is the rank for representing c macros introduced in our headers.
|
|
///
|
|
/// The key is the name of the macro.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /macro/__attribute__
|
|
/// /macro/_PACKED
|
|
/// /macro/_ABI
|
|
/// ```
|
|
inline auto Macro = defineRank<"macro", std::string>(Binary);
|
|
|
|
/// This is the rank for representing opaque types wrapping model array types
|
|
///
|
|
/// The key is the byte size of the wrapped type.
|
|
///
|
|
/// Examples:
|
|
/// ```
|
|
/// /opaque-type/8
|
|
/// ```
|
|
inline auto OpaqueType = defineRank<"opaque-type", uint64_t>(Binary);
|
|
|
|
} // namespace revng::ranks
|