mirror of
https://github.com/WerWolv/ImHex.git
synced 2026-03-27 23:37:05 -05:00
impr: General code cleanup
This commit is contained in:
2
lib/external/libromfs
vendored
2
lib/external/libromfs
vendored
Submodule lib/external/libromfs updated: c42309b7c4...84edc66e4c
2
lib/external/libwolv
vendored
2
lib/external/libwolv
vendored
Submodule lib/external/libwolv updated: 56242ac37f...86faee9f3e
@@ -11,6 +11,7 @@
|
||||
|
||||
#include <cstddef>
|
||||
#include <string>
|
||||
#include <string_view>
|
||||
|
||||
namespace llvm {
|
||||
/// This is a llvm local version of __cxa_demangle. Other than the name and
|
||||
@@ -28,8 +29,10 @@ enum : int {
|
||||
demangle_success = 0,
|
||||
};
|
||||
|
||||
char *itaniumDemangle(const char *mangled_name, char *buf, size_t *n,
|
||||
int *status);
|
||||
/// Returns a non-NULL pointer to a NUL-terminated C style string
|
||||
/// that should be explicitly freed, if successful. Otherwise, may return
|
||||
/// nullptr if mangled_name is not a valid mangling or is nullptr.
|
||||
char *itaniumDemangle(std::string_view mangled_name);
|
||||
|
||||
enum MSDemangleFlags {
|
||||
MSDF_None = 0,
|
||||
@@ -46,31 +49,25 @@ enum MSDemangleFlags {
|
||||
/// success, or nullptr on error.
|
||||
/// If n_read is non-null and demangling was successful, it receives how many
|
||||
/// bytes of the input string were consumed.
|
||||
/// buf can point to a *n_buf bytes large buffer where the demangled name is
|
||||
/// stored. If the buffer is too small, it is grown with realloc(). If buf is
|
||||
/// nullptr, then this malloc()s memory for the result.
|
||||
/// *n_buf stores the size of buf on input if buf is non-nullptr, and it
|
||||
/// receives the size of the demangled string on output if n_buf is not nullptr.
|
||||
/// status receives one of the demangle_ enum entries above if it's not nullptr.
|
||||
/// Flags controls various details of the demangled representation.
|
||||
char *microsoftDemangle(const char *mangled_name, size_t *n_read, char *buf,
|
||||
size_t *n_buf, int *status,
|
||||
MSDemangleFlags Flags = MSDF_None);
|
||||
char *microsoftDemangle(std::string_view mangled_name, size_t *n_read,
|
||||
int *status, MSDemangleFlags Flags = MSDF_None);
|
||||
|
||||
// Demangles a Rust v0 mangled symbol.
|
||||
char *rustDemangle(const char *MangledName);
|
||||
char *rustDemangle(std::string_view MangledName);
|
||||
|
||||
// Demangles a D mangled symbol.
|
||||
char *dlangDemangle(const char *MangledName);
|
||||
char *dlangDemangle(std::string_view MangledName);
|
||||
|
||||
/// Attempt to demangle a string using different demangling schemes.
|
||||
/// The function uses heuristics to determine which demangling scheme to use.
|
||||
/// \param MangledName - reference to string to demangle.
|
||||
/// \returns - the demangled string, or a copy of the input string if no
|
||||
/// demangling occurred.
|
||||
std::string demangle(const std::string &MangledName);
|
||||
std::string demangle(std::string_view MangledName);
|
||||
|
||||
bool nonMicrosoftDemangle(const char *MangledName, std::string &Result);
|
||||
bool nonMicrosoftDemangle(std::string_view MangledName, std::string &Result);
|
||||
|
||||
/// "Partial" demangler. This supports demangling a string into an AST
|
||||
/// (typically an intermediate stage in itaniumDemangle) and querying certain
|
||||
@@ -87,7 +84,7 @@ struct ItaniumPartialDemangler {
|
||||
bool partialDemangle(const char *MangledName);
|
||||
|
||||
/// Just print the entire mangled name into Buf. Buf and N behave like the
|
||||
/// second and third parameters to itaniumDemangle.
|
||||
/// second and third parameters to __cxa_demangle.
|
||||
char *finishDemangle(char *Buf, size_t *N) const;
|
||||
|
||||
/// Get the base name of a function. This doesn't include trailing template
|
||||
|
||||
@@ -13,11 +13,11 @@
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_DEMANGLE_ITANIUMDEMANGLE_H
|
||||
#define LLVM_DEMANGLE_ITANIUMDEMANGLE_H
|
||||
#ifndef DEMANGLE_ITANIUMDEMANGLE_H
|
||||
#define DEMANGLE_ITANIUMDEMANGLE_H
|
||||
|
||||
#include "DemangleConfig.h"
|
||||
#include "StringView.h"
|
||||
#include "StringViewExtras.h"
|
||||
#include "Utility.h"
|
||||
#include <algorithm>
|
||||
#include <cassert>
|
||||
@@ -26,6 +26,9 @@
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <limits>
|
||||
#include <new>
|
||||
#include <string_view>
|
||||
#include <type_traits>
|
||||
#include <utility>
|
||||
|
||||
DEMANGLE_NAMESPACE_BEGIN
|
||||
@@ -285,7 +288,7 @@ public:
|
||||
// implementation.
|
||||
virtual void printRight(OutputBuffer &) const {}
|
||||
|
||||
virtual StringView getBaseName() const { return StringView(); }
|
||||
virtual std::string_view getBaseName() const { return {}; }
|
||||
|
||||
// Silence compiler warnings, this dtor will never be called.
|
||||
virtual ~Node() = default;
|
||||
@@ -344,10 +347,10 @@ struct NodeArrayNode : Node {
|
||||
|
||||
class DotSuffix final : public Node {
|
||||
const Node *Prefix;
|
||||
const StringView Suffix;
|
||||
const std::string_view Suffix;
|
||||
|
||||
public:
|
||||
DotSuffix(const Node *Prefix_, StringView Suffix_)
|
||||
DotSuffix(const Node *Prefix_, std::string_view Suffix_)
|
||||
: Node(KDotSuffix), Prefix(Prefix_), Suffix(Suffix_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Prefix, Suffix); }
|
||||
@@ -362,15 +365,15 @@ public:
|
||||
|
||||
class VendorExtQualType final : public Node {
|
||||
const Node *Ty;
|
||||
StringView Ext;
|
||||
std::string_view Ext;
|
||||
const Node *TA;
|
||||
|
||||
public:
|
||||
VendorExtQualType(const Node *Ty_, StringView Ext_, const Node *TA_)
|
||||
VendorExtQualType(const Node *Ty_, std::string_view Ext_, const Node *TA_)
|
||||
: Node(KVendorExtQualType), Ty(Ty_), Ext(Ext_), TA(TA_) {}
|
||||
|
||||
const Node *getTy() const { return Ty; }
|
||||
StringView getExt() const { return Ext; }
|
||||
std::string_view getExt() const { return Ext; }
|
||||
const Node *getTA() const { return TA; }
|
||||
|
||||
template <typename Fn> void match(Fn F) const { F(Ty, Ext, TA); }
|
||||
@@ -461,10 +464,10 @@ public:
|
||||
|
||||
class PostfixQualifiedType final : public Node {
|
||||
const Node *Ty;
|
||||
const StringView Postfix;
|
||||
const std::string_view Postfix;
|
||||
|
||||
public:
|
||||
PostfixQualifiedType(const Node *Ty_, StringView Postfix_)
|
||||
PostfixQualifiedType(const Node *Ty_, std::string_view Postfix_)
|
||||
: Node(KPostfixQualifiedType), Ty(Ty_), Postfix(Postfix_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Ty, Postfix); }
|
||||
@@ -476,15 +479,15 @@ public:
|
||||
};
|
||||
|
||||
class NameType final : public Node {
|
||||
const StringView Name;
|
||||
const std::string_view Name;
|
||||
|
||||
public:
|
||||
NameType(StringView Name_) : Node(KNameType), Name(Name_) {}
|
||||
NameType(std::string_view Name_) : Node(KNameType), Name(Name_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Name); }
|
||||
|
||||
StringView getName() const { return Name; }
|
||||
StringView getBaseName() const override { return Name; }
|
||||
std::string_view getName() const { return Name; }
|
||||
std::string_view getBaseName() const override { return Name; }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override { OB += Name; }
|
||||
};
|
||||
@@ -510,10 +513,10 @@ public:
|
||||
};
|
||||
|
||||
class ElaboratedTypeSpefType : public Node {
|
||||
StringView Kind;
|
||||
std::string_view Kind;
|
||||
Node *Child;
|
||||
public:
|
||||
ElaboratedTypeSpefType(StringView Kind_, Node *Child_)
|
||||
ElaboratedTypeSpefType(std::string_view Kind_, Node *Child_)
|
||||
: Node(KElaboratedTypeSpefType), Kind(Kind_), Child(Child_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Kind, Child); }
|
||||
@@ -527,15 +530,17 @@ public:
|
||||
|
||||
struct AbiTagAttr : Node {
|
||||
Node *Base;
|
||||
StringView Tag;
|
||||
std::string_view Tag;
|
||||
|
||||
AbiTagAttr(Node* Base_, StringView Tag_)
|
||||
: Node(KAbiTagAttr, Base_->RHSComponentCache,
|
||||
Base_->ArrayCache, Base_->FunctionCache),
|
||||
AbiTagAttr(Node *Base_, std::string_view Tag_)
|
||||
: Node(KAbiTagAttr, Base_->RHSComponentCache, Base_->ArrayCache,
|
||||
Base_->FunctionCache),
|
||||
Base(Base_), Tag(Tag_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Base, Tag); }
|
||||
|
||||
std::string_view getBaseName() const override { return Base->getBaseName(); }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override {
|
||||
Base->printLeft(OB);
|
||||
OB += "[abi:";
|
||||
@@ -561,12 +566,12 @@ public:
|
||||
|
||||
class ObjCProtoName : public Node {
|
||||
const Node *Ty;
|
||||
StringView Protocol;
|
||||
std::string_view Protocol;
|
||||
|
||||
friend class PointerType;
|
||||
|
||||
public:
|
||||
ObjCProtoName(const Node *Ty_, StringView Protocol_)
|
||||
ObjCProtoName(const Node *Ty_, std::string_view Protocol_)
|
||||
: Node(KObjCProtoName), Ty(Ty_), Protocol(Protocol_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Ty, Protocol); }
|
||||
@@ -943,11 +948,11 @@ public:
|
||||
};
|
||||
|
||||
class SpecialName final : public Node {
|
||||
const StringView Special;
|
||||
const std::string_view Special;
|
||||
const Node *Child;
|
||||
|
||||
public:
|
||||
SpecialName(StringView Special_, const Node *Child_)
|
||||
SpecialName(std::string_view Special_, const Node *Child_)
|
||||
: Node(KSpecialName), Special(Special_), Child(Child_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Special, Child); }
|
||||
@@ -986,7 +991,7 @@ struct NestedName : Node {
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Qual, Name); }
|
||||
|
||||
StringView getBaseName() const override { return Name->getBaseName(); }
|
||||
std::string_view getBaseName() const override { return Name->getBaseName(); }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override {
|
||||
Qual->print(OB);
|
||||
@@ -1026,7 +1031,7 @@ struct ModuleEntity : Node {
|
||||
|
||||
template <typename Fn> void match(Fn F) const { F(Module, Name); }
|
||||
|
||||
StringView getBaseName() const override { return Name->getBaseName(); }
|
||||
std::string_view getBaseName() const override { return Name->getBaseName(); }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override {
|
||||
Name->print(OB);
|
||||
@@ -1062,7 +1067,7 @@ public:
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Qualifier, Name); }
|
||||
|
||||
StringView getBaseName() const override { return Name->getBaseName(); }
|
||||
std::string_view getBaseName() const override { return Name->getBaseName(); }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override {
|
||||
Qualifier->print(OB);
|
||||
@@ -1484,7 +1489,7 @@ struct NameWithTemplateArgs : Node {
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Name, TemplateArgs); }
|
||||
|
||||
StringView getBaseName() const override { return Name->getBaseName(); }
|
||||
std::string_view getBaseName() const override { return Name->getBaseName(); }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override {
|
||||
Name->print(OB);
|
||||
@@ -1501,7 +1506,7 @@ public:
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Child); }
|
||||
|
||||
StringView getBaseName() const override { return Child->getBaseName(); }
|
||||
std::string_view getBaseName() const override { return Child->getBaseName(); }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override {
|
||||
OB += "::";
|
||||
@@ -1537,20 +1542,20 @@ protected:
|
||||
return unsigned(SSK) >= unsigned(SpecialSubKind::string);
|
||||
}
|
||||
|
||||
StringView getBaseName() const override {
|
||||
std::string_view getBaseName() const override {
|
||||
switch (SSK) {
|
||||
case SpecialSubKind::allocator:
|
||||
return StringView("allocator");
|
||||
return {"allocator"};
|
||||
case SpecialSubKind::basic_string:
|
||||
return StringView("basic_string");
|
||||
return {"basic_string"};
|
||||
case SpecialSubKind::string:
|
||||
return StringView("basic_string");
|
||||
return {"basic_string"};
|
||||
case SpecialSubKind::istream:
|
||||
return StringView("basic_istream");
|
||||
return {"basic_istream"};
|
||||
case SpecialSubKind::ostream:
|
||||
return StringView("basic_ostream");
|
||||
return {"basic_ostream"};
|
||||
case SpecialSubKind::iostream:
|
||||
return StringView("basic_iostream");
|
||||
return {"basic_iostream"};
|
||||
}
|
||||
DEMANGLE_UNREACHABLE;
|
||||
}
|
||||
@@ -1574,12 +1579,12 @@ public:
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(SSK); }
|
||||
|
||||
StringView getBaseName() const override {
|
||||
auto SV = ExpandedSpecialSubstitution::getBaseName ();
|
||||
std::string_view getBaseName() const override {
|
||||
std::string_view SV = ExpandedSpecialSubstitution::getBaseName();
|
||||
if (isInstantiation()) {
|
||||
// The instantiations are typedefs that drop the "basic_" prefix.
|
||||
assert(SV.startsWith("basic_"));
|
||||
SV = SV.dropFront(sizeof("basic_") - 1);
|
||||
assert(llvm::itanium_demangle::starts_with(SV, "basic_"));
|
||||
SV.remove_prefix(sizeof("basic_") - 1);
|
||||
}
|
||||
return SV;
|
||||
}
|
||||
@@ -1627,10 +1632,11 @@ public:
|
||||
};
|
||||
|
||||
class UnnamedTypeName : public Node {
|
||||
const StringView Count;
|
||||
const std::string_view Count;
|
||||
|
||||
public:
|
||||
UnnamedTypeName(StringView Count_) : Node(KUnnamedTypeName), Count(Count_) {}
|
||||
UnnamedTypeName(std::string_view Count_)
|
||||
: Node(KUnnamedTypeName), Count(Count_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Count); }
|
||||
|
||||
@@ -1644,11 +1650,11 @@ public:
|
||||
class ClosureTypeName : public Node {
|
||||
NodeArray TemplateParams;
|
||||
NodeArray Params;
|
||||
StringView Count;
|
||||
std::string_view Count;
|
||||
|
||||
public:
|
||||
ClosureTypeName(NodeArray TemplateParams_, NodeArray Params_,
|
||||
StringView Count_)
|
||||
std::string_view Count_)
|
||||
: Node(KClosureTypeName), TemplateParams(TemplateParams_),
|
||||
Params(Params_), Count(Count_) {}
|
||||
|
||||
@@ -1695,12 +1701,12 @@ public:
|
||||
|
||||
class BinaryExpr : public Node {
|
||||
const Node *LHS;
|
||||
const StringView InfixOperator;
|
||||
const std::string_view InfixOperator;
|
||||
const Node *RHS;
|
||||
|
||||
public:
|
||||
BinaryExpr(const Node *LHS_, StringView InfixOperator_, const Node *RHS_,
|
||||
Prec Prec_)
|
||||
BinaryExpr(const Node *LHS_, std::string_view InfixOperator_,
|
||||
const Node *RHS_, Prec Prec_)
|
||||
: Node(KBinaryExpr, Prec_), LHS(LHS_), InfixOperator(InfixOperator_),
|
||||
RHS(RHS_) {}
|
||||
|
||||
@@ -1749,10 +1755,10 @@ public:
|
||||
|
||||
class PostfixExpr : public Node {
|
||||
const Node *Child;
|
||||
const StringView Operator;
|
||||
const std::string_view Operator;
|
||||
|
||||
public:
|
||||
PostfixExpr(const Node *Child_, StringView Operator_, Prec Prec_)
|
||||
PostfixExpr(const Node *Child_, std::string_view Operator_, Prec Prec_)
|
||||
: Node(KPostfixExpr, Prec_), Child(Child_), Operator(Operator_) {}
|
||||
|
||||
template <typename Fn> void match(Fn F) const {
|
||||
@@ -1790,11 +1796,12 @@ public:
|
||||
|
||||
class MemberExpr : public Node {
|
||||
const Node *LHS;
|
||||
const StringView Kind;
|
||||
const std::string_view Kind;
|
||||
const Node *RHS;
|
||||
|
||||
public:
|
||||
MemberExpr(const Node *LHS_, StringView Kind_, const Node *RHS_, Prec Prec_)
|
||||
MemberExpr(const Node *LHS_, std::string_view Kind_, const Node *RHS_,
|
||||
Prec Prec_)
|
||||
: Node(KMemberExpr, Prec_), LHS(LHS_), Kind(Kind_), RHS(RHS_) {}
|
||||
|
||||
template <typename Fn> void match(Fn F) const {
|
||||
@@ -1811,13 +1818,14 @@ public:
|
||||
class SubobjectExpr : public Node {
|
||||
const Node *Type;
|
||||
const Node *SubExpr;
|
||||
StringView Offset;
|
||||
std::string_view Offset;
|
||||
NodeArray UnionSelectors;
|
||||
bool OnePastTheEnd;
|
||||
|
||||
public:
|
||||
SubobjectExpr(const Node *Type_, const Node *SubExpr_, StringView Offset_,
|
||||
NodeArray UnionSelectors_, bool OnePastTheEnd_)
|
||||
SubobjectExpr(const Node *Type_, const Node *SubExpr_,
|
||||
std::string_view Offset_, NodeArray UnionSelectors_,
|
||||
bool OnePastTheEnd_)
|
||||
: Node(KSubobjectExpr), Type(Type_), SubExpr(SubExpr_), Offset(Offset_),
|
||||
UnionSelectors(UnionSelectors_), OnePastTheEnd(OnePastTheEnd_) {}
|
||||
|
||||
@@ -1834,7 +1842,7 @@ public:
|
||||
OB += "0";
|
||||
} else if (Offset[0] == 'n') {
|
||||
OB += "-";
|
||||
OB += Offset.dropFront();
|
||||
OB += std::string_view(Offset.data() + 1, Offset.size() - 1);
|
||||
} else {
|
||||
OB += Offset;
|
||||
}
|
||||
@@ -1843,12 +1851,12 @@ public:
|
||||
};
|
||||
|
||||
class EnclosingExpr : public Node {
|
||||
const StringView Prefix;
|
||||
const std::string_view Prefix;
|
||||
const Node *Infix;
|
||||
const StringView Postfix;
|
||||
const std::string_view Postfix;
|
||||
|
||||
public:
|
||||
EnclosingExpr(StringView Prefix_, const Node *Infix_,
|
||||
EnclosingExpr(std::string_view Prefix_, const Node *Infix_,
|
||||
Prec Prec_ = Prec::Primary)
|
||||
: Node(KEnclosingExpr, Prec_), Prefix(Prefix_), Infix(Infix_) {}
|
||||
|
||||
@@ -1867,12 +1875,13 @@ public:
|
||||
|
||||
class CastExpr : public Node {
|
||||
// cast_kind<to>(from)
|
||||
const StringView CastKind;
|
||||
const std::string_view CastKind;
|
||||
const Node *To;
|
||||
const Node *From;
|
||||
|
||||
public:
|
||||
CastExpr(StringView CastKind_, const Node *To_, const Node *From_, Prec Prec_)
|
||||
CastExpr(std::string_view CastKind_, const Node *To_, const Node *From_,
|
||||
Prec Prec_)
|
||||
: Node(KCastExpr, Prec_), CastKind(CastKind_), To(To_), From(From_) {}
|
||||
|
||||
template <typename Fn> void match(Fn F) const {
|
||||
@@ -1995,11 +2004,11 @@ public:
|
||||
};
|
||||
|
||||
class PrefixExpr : public Node {
|
||||
StringView Prefix;
|
||||
std::string_view Prefix;
|
||||
Node *Child;
|
||||
|
||||
public:
|
||||
PrefixExpr(StringView Prefix_, Node *Child_, Prec Prec_)
|
||||
PrefixExpr(std::string_view Prefix_, Node *Child_, Prec Prec_)
|
||||
: Node(KPrefixExpr, Prec_), Prefix(Prefix_), Child(Child_) {}
|
||||
|
||||
template <typename Fn> void match(Fn F) const {
|
||||
@@ -2013,10 +2022,11 @@ public:
|
||||
};
|
||||
|
||||
class FunctionParam : public Node {
|
||||
StringView Number;
|
||||
std::string_view Number;
|
||||
|
||||
public:
|
||||
FunctionParam(StringView Number_) : Node(KFunctionParam), Number(Number_) {}
|
||||
FunctionParam(std::string_view Number_)
|
||||
: Node(KFunctionParam), Number(Number_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Number); }
|
||||
|
||||
@@ -2051,11 +2061,11 @@ public:
|
||||
class PointerToMemberConversionExpr : public Node {
|
||||
const Node *Type;
|
||||
const Node *SubExpr;
|
||||
StringView Offset;
|
||||
std::string_view Offset;
|
||||
|
||||
public:
|
||||
PointerToMemberConversionExpr(const Node *Type_, const Node *SubExpr_,
|
||||
StringView Offset_, Prec Prec_)
|
||||
std::string_view Offset_, Prec Prec_)
|
||||
: Node(KPointerToMemberConversionExpr, Prec_), Type(Type_),
|
||||
SubExpr(SubExpr_), Offset(Offset_) {}
|
||||
|
||||
@@ -2140,11 +2150,11 @@ public:
|
||||
|
||||
class FoldExpr : public Node {
|
||||
const Node *Pack, *Init;
|
||||
StringView OperatorName;
|
||||
std::string_view OperatorName;
|
||||
bool IsLeftFold;
|
||||
|
||||
public:
|
||||
FoldExpr(bool IsLeftFold_, StringView OperatorName_, const Node *Pack_,
|
||||
FoldExpr(bool IsLeftFold_, std::string_view OperatorName_, const Node *Pack_,
|
||||
const Node *Init_)
|
||||
: Node(KFoldExpr), Pack(Pack_), Init(Init_), OperatorName(OperatorName_),
|
||||
IsLeftFold(IsLeftFold_) {}
|
||||
@@ -2208,7 +2218,7 @@ public:
|
||||
template<typename Fn> void match(Fn F) const { F(Value); }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override {
|
||||
OB += Value ? StringView("true") : StringView("false");
|
||||
OB += Value ? std::string_view("true") : std::string_view("false");
|
||||
}
|
||||
};
|
||||
|
||||
@@ -2246,10 +2256,10 @@ public:
|
||||
class EnumLiteral : public Node {
|
||||
// ty(integer)
|
||||
const Node *Ty;
|
||||
StringView Integer;
|
||||
std::string_view Integer;
|
||||
|
||||
public:
|
||||
EnumLiteral(const Node *Ty_, StringView Integer_)
|
||||
EnumLiteral(const Node *Ty_, std::string_view Integer_)
|
||||
: Node(KEnumLiteral), Ty(Ty_), Integer(Integer_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Ty, Integer); }
|
||||
@@ -2260,18 +2270,18 @@ public:
|
||||
OB.printClose();
|
||||
|
||||
if (Integer[0] == 'n')
|
||||
OB << "-" << Integer.dropFront(1);
|
||||
OB << '-' << std::string_view(Integer.data() + 1, Integer.size() - 1);
|
||||
else
|
||||
OB << Integer;
|
||||
}
|
||||
};
|
||||
|
||||
class IntegerLiteral : public Node {
|
||||
StringView Type;
|
||||
StringView Value;
|
||||
std::string_view Type;
|
||||
std::string_view Value;
|
||||
|
||||
public:
|
||||
IntegerLiteral(StringView Type_, StringView Value_)
|
||||
IntegerLiteral(std::string_view Type_, std::string_view Value_)
|
||||
: Node(KIntegerLiteral), Type(Type_), Value(Value_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Type, Value); }
|
||||
@@ -2283,10 +2293,9 @@ public:
|
||||
OB.printClose();
|
||||
}
|
||||
|
||||
if (Value[0] == 'n') {
|
||||
OB += '-';
|
||||
OB += Value.dropFront(1);
|
||||
} else
|
||||
if (Value[0] == 'n')
|
||||
OB << '-' << std::string_view(Value.data() + 1, Value.size() - 1);
|
||||
else
|
||||
OB += Value;
|
||||
|
||||
if (Type.size() <= 3)
|
||||
@@ -2309,29 +2318,26 @@ constexpr Node::Kind getFloatLiteralKind(long double *) {
|
||||
}
|
||||
|
||||
template <class Float> class FloatLiteralImpl : public Node {
|
||||
const StringView Contents;
|
||||
const std::string_view Contents;
|
||||
|
||||
static constexpr Kind KindForClass =
|
||||
float_literal_impl::getFloatLiteralKind((Float *)nullptr);
|
||||
|
||||
public:
|
||||
FloatLiteralImpl(StringView Contents_)
|
||||
FloatLiteralImpl(std::string_view Contents_)
|
||||
: Node(KindForClass), Contents(Contents_) {}
|
||||
|
||||
template<typename Fn> void match(Fn F) const { F(Contents); }
|
||||
|
||||
void printLeft(OutputBuffer &OB) const override {
|
||||
const char *first = Contents.begin();
|
||||
const char *last = Contents.end() + 1;
|
||||
|
||||
const size_t N = FloatData<Float>::mangled_size;
|
||||
if (static_cast<std::size_t>(last - first) > N) {
|
||||
last = first + N;
|
||||
if (Contents.size() >= N) {
|
||||
union {
|
||||
Float value;
|
||||
char buf[sizeof(Float)];
|
||||
};
|
||||
const char *t = first;
|
||||
const char *t = Contents.data();
|
||||
const char *last = t + N;
|
||||
char *e = buf;
|
||||
for (; t != last; ++t, ++e) {
|
||||
unsigned d1 = isdigit(*t) ? static_cast<unsigned>(*t - '0')
|
||||
@@ -2346,7 +2352,7 @@ public:
|
||||
#endif
|
||||
char num[FloatData<Float>::max_demangled_size] = {0};
|
||||
int n = snprintf(num, sizeof(num), FloatData<Float>::spec, value);
|
||||
OB += StringView(num, num + n);
|
||||
OB += std::string_view(num, n);
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -2473,8 +2479,9 @@ template <typename Derived, typename Alloc> struct AbstractManglingParser {
|
||||
return res;
|
||||
}
|
||||
|
||||
bool consumeIf(StringView S) {
|
||||
if (StringView(First, Last).startsWith(S)) {
|
||||
bool consumeIf(std::string_view S) {
|
||||
if (llvm::itanium_demangle::starts_with(
|
||||
std::string_view(First, Last - First), S)) {
|
||||
First += S.size();
|
||||
return true;
|
||||
}
|
||||
@@ -2499,10 +2506,10 @@ template <typename Derived, typename Alloc> struct AbstractManglingParser {
|
||||
|
||||
size_t numLeft() const { return static_cast<size_t>(Last - First); }
|
||||
|
||||
StringView parseNumber(bool AllowNegative = false);
|
||||
std::string_view parseNumber(bool AllowNegative = false);
|
||||
Qualifiers parseCVQualifiers();
|
||||
bool parsePositiveInteger(size_t *Out);
|
||||
StringView parseBareSourceName();
|
||||
std::string_view parseBareSourceName();
|
||||
|
||||
bool parseSeqId(size_t *Out);
|
||||
Node *parseSubstitution();
|
||||
@@ -2513,9 +2520,9 @@ template <typename Derived, typename Alloc> struct AbstractManglingParser {
|
||||
|
||||
/// Parse the <expr> production.
|
||||
Node *parseExpr();
|
||||
Node *parsePrefixExpr(StringView Kind, Node::Prec Prec);
|
||||
Node *parseBinaryExpr(StringView Kind, Node::Prec Prec);
|
||||
Node *parseIntegerLiteral(StringView Lit);
|
||||
Node *parsePrefixExpr(std::string_view Kind, Node::Prec Prec);
|
||||
Node *parseBinaryExpr(std::string_view Kind, Node::Prec Prec);
|
||||
Node *parseIntegerLiteral(std::string_view Lit);
|
||||
Node *parseExprPrimary();
|
||||
template <class Float> Node *parseFloatingLiteral();
|
||||
Node *parseFunctionParam();
|
||||
@@ -2623,17 +2630,18 @@ template <typename Derived, typename Alloc> struct AbstractManglingParser {
|
||||
bool operator!=(const char *Peek) const { return !this->operator==(Peek); }
|
||||
|
||||
public:
|
||||
StringView getSymbol() const {
|
||||
StringView Res = Name;
|
||||
std::string_view getSymbol() const {
|
||||
std::string_view Res = Name;
|
||||
if (Kind < Unnameable) {
|
||||
assert(Res.startsWith("operator") &&
|
||||
assert(llvm::itanium_demangle::starts_with(Res, "operator") &&
|
||||
"operator name does not start with 'operator'");
|
||||
Res = Res.dropFront(sizeof("operator") - 1);
|
||||
Res.consumeFront(' ');
|
||||
Res.remove_prefix(sizeof("operator") - 1);
|
||||
if (llvm::itanium_demangle::starts_with(Res, ' '))
|
||||
Res.remove_prefix(1);
|
||||
}
|
||||
return Res;
|
||||
}
|
||||
StringView getName() const { return Name; }
|
||||
std::string_view getName() const { return Name; }
|
||||
OIKind getKind() const { return Kind; }
|
||||
bool getFlag() const { return Flag; }
|
||||
Node::Prec getPrecedence() const { return Prec; }
|
||||
@@ -2853,7 +2861,7 @@ AbstractManglingParser<Derived, Alloc>::parseUnnamedTypeName(NameState *State) {
|
||||
TemplateParams.clear();
|
||||
|
||||
if (consumeIf("Ut")) {
|
||||
StringView Count = parseNumber();
|
||||
std::string_view Count = parseNumber();
|
||||
if (!consumeIf('_'))
|
||||
return nullptr;
|
||||
return make<UnnamedTypeName>(Count);
|
||||
@@ -2865,7 +2873,7 @@ AbstractManglingParser<Derived, Alloc>::parseUnnamedTypeName(NameState *State) {
|
||||
|
||||
size_t ParamsBegin = Names.size();
|
||||
while (look() == 'T' &&
|
||||
StringView("yptn").find(look(1)) != StringView::npos) {
|
||||
std::string_view("yptn").find(look(1)) != std::string_view::npos) {
|
||||
Node *T = parseTemplateParamDecl();
|
||||
if (!T)
|
||||
return nullptr;
|
||||
@@ -2908,7 +2916,7 @@ AbstractManglingParser<Derived, Alloc>::parseUnnamedTypeName(NameState *State) {
|
||||
}
|
||||
NodeArray Params = popTrailingNodeArray(ParamsBegin);
|
||||
|
||||
StringView Count = parseNumber();
|
||||
std::string_view Count = parseNumber();
|
||||
if (!consumeIf('_'))
|
||||
return nullptr;
|
||||
return make<ClosureTypeName>(TempParams, Params, Count);
|
||||
@@ -2930,9 +2938,9 @@ Node *AbstractManglingParser<Derived, Alloc>::parseSourceName(NameState *) {
|
||||
return nullptr;
|
||||
if (numLeft() < Length || Length == 0)
|
||||
return nullptr;
|
||||
StringView Name(First, First + Length);
|
||||
std::string_view Name(First, Length);
|
||||
First += Length;
|
||||
if (Name.startsWith("_GLOBAL__N"))
|
||||
if (llvm::itanium_demangle::starts_with(Name, "_GLOBAL__N"))
|
||||
return make<NameType>("(anonymous namespace)");
|
||||
return make<NameType>(Name);
|
||||
}
|
||||
@@ -3031,14 +3039,21 @@ AbstractManglingParser<Derived, Alloc>::parseOperatorEncoding() {
|
||||
if (numLeft() < 2)
|
||||
return nullptr;
|
||||
|
||||
auto Op = std::lower_bound(
|
||||
&Ops[0], &Ops[NumOps], First,
|
||||
[](const OperatorInfo &Op_, const char *Enc_) { return Op_ < Enc_; });
|
||||
if (Op == &Ops[NumOps] || *Op != First)
|
||||
// We can't use lower_bound as that can link to symbols in the C++ library,
|
||||
// and this must remain independant of that.
|
||||
size_t lower = 0u, upper = NumOps - 1; // Inclusive bounds.
|
||||
while (upper != lower) {
|
||||
size_t middle = (upper + lower) / 2;
|
||||
if (Ops[middle] < First)
|
||||
lower = middle + 1;
|
||||
else
|
||||
upper = middle;
|
||||
}
|
||||
if (Ops[lower] != First)
|
||||
return nullptr;
|
||||
|
||||
First += 2;
|
||||
return Op;
|
||||
return &Ops[lower];
|
||||
}
|
||||
|
||||
// <operator-name> ::= See parseOperatorEncoding()
|
||||
@@ -3439,7 +3454,7 @@ Node *AbstractManglingParser<Derived, Alloc>::parseUnresolvedName(bool Global) {
|
||||
template <typename Derived, typename Alloc>
|
||||
Node *AbstractManglingParser<Derived, Alloc>::parseAbiTags(Node *N) {
|
||||
while (consumeIf('B')) {
|
||||
StringView SN = parseBareSourceName();
|
||||
std::string_view SN = parseBareSourceName();
|
||||
if (SN.empty())
|
||||
return nullptr;
|
||||
N = make<AbiTagAttr>(N, SN);
|
||||
@@ -3451,16 +3466,16 @@ Node *AbstractManglingParser<Derived, Alloc>::parseAbiTags(Node *N) {
|
||||
|
||||
// <number> ::= [n] <non-negative decimal integer>
|
||||
template <typename Alloc, typename Derived>
|
||||
StringView
|
||||
std::string_view
|
||||
AbstractManglingParser<Alloc, Derived>::parseNumber(bool AllowNegative) {
|
||||
const char *Tmp = First;
|
||||
if (AllowNegative)
|
||||
consumeIf('n');
|
||||
if (numLeft() == 0 || !std::isdigit(*First))
|
||||
return StringView();
|
||||
return std::string_view();
|
||||
while (numLeft() != 0 && std::isdigit(*First))
|
||||
++First;
|
||||
return StringView(Tmp, First);
|
||||
return std::string_view(Tmp, First - Tmp);
|
||||
}
|
||||
|
||||
// <positive length number> ::= [0-9]*
|
||||
@@ -3477,11 +3492,11 @@ bool AbstractManglingParser<Alloc, Derived>::parsePositiveInteger(size_t *Out) {
|
||||
}
|
||||
|
||||
template <typename Alloc, typename Derived>
|
||||
StringView AbstractManglingParser<Alloc, Derived>::parseBareSourceName() {
|
||||
std::string_view AbstractManglingParser<Alloc, Derived>::parseBareSourceName() {
|
||||
size_t Int = 0;
|
||||
if (parsePositiveInteger(&Int) || numLeft() < Int)
|
||||
return StringView();
|
||||
StringView R(First, First + Int);
|
||||
return {};
|
||||
std::string_view R(First, Int);
|
||||
First += Int;
|
||||
return R;
|
||||
}
|
||||
@@ -3665,7 +3680,7 @@ Node *AbstractManglingParser<Derived, Alloc>::parsePointerToMemberType() {
|
||||
// ::= Te <name> # dependent elaborated type specifier using 'enum'
|
||||
template <typename Derived, typename Alloc>
|
||||
Node *AbstractManglingParser<Derived, Alloc>::parseClassEnumType() {
|
||||
StringView ElabSpef;
|
||||
std::string_view ElabSpef;
|
||||
if (consumeIf("Ts"))
|
||||
ElabSpef = "struct";
|
||||
else if (consumeIf("Tu"))
|
||||
@@ -3689,17 +3704,18 @@ Node *AbstractManglingParser<Derived, Alloc>::parseClassEnumType() {
|
||||
template <typename Derived, typename Alloc>
|
||||
Node *AbstractManglingParser<Derived, Alloc>::parseQualifiedType() {
|
||||
if (consumeIf('U')) {
|
||||
StringView Qual = parseBareSourceName();
|
||||
std::string_view Qual = parseBareSourceName();
|
||||
if (Qual.empty())
|
||||
return nullptr;
|
||||
|
||||
// extension ::= U <objc-name> <objc-type> # objc-type<identifier>
|
||||
if (Qual.startsWith("objcproto")) {
|
||||
StringView ProtoSourceName = Qual.dropFront(std::strlen("objcproto"));
|
||||
StringView Proto;
|
||||
if (llvm::itanium_demangle::starts_with(Qual, "objcproto")) {
|
||||
constexpr size_t Len = sizeof("objcproto") - 1;
|
||||
std::string_view ProtoSourceName(Qual.data() + Len, Qual.size() - Len);
|
||||
std::string_view Proto;
|
||||
{
|
||||
ScopedOverride<const char *> SaveFirst(First, ProtoSourceName.begin()),
|
||||
SaveLast(Last, ProtoSourceName.end());
|
||||
ScopedOverride<const char *> SaveFirst(First, ProtoSourceName.data()),
|
||||
SaveLast(Last, &*ProtoSourceName.rbegin() + 1);
|
||||
Proto = parseBareSourceName();
|
||||
}
|
||||
if (Proto.empty())
|
||||
@@ -3867,7 +3883,7 @@ Node *AbstractManglingParser<Derived, Alloc>::parseType() {
|
||||
// <builtin-type> ::= u <source-name> # vendor extended type
|
||||
case 'u': {
|
||||
++First;
|
||||
StringView Res = parseBareSourceName();
|
||||
std::string_view Res = parseBareSourceName();
|
||||
if (Res.empty())
|
||||
return nullptr;
|
||||
// Typically, <builtin-type>s are not considered substitution candidates,
|
||||
@@ -4115,8 +4131,9 @@ Node *AbstractManglingParser<Derived, Alloc>::parseType() {
|
||||
}
|
||||
|
||||
template <typename Derived, typename Alloc>
|
||||
Node *AbstractManglingParser<Derived, Alloc>::parsePrefixExpr(StringView Kind,
|
||||
Node::Prec Prec) {
|
||||
Node *
|
||||
AbstractManglingParser<Derived, Alloc>::parsePrefixExpr(std::string_view Kind,
|
||||
Node::Prec Prec) {
|
||||
Node *E = getDerived().parseExpr();
|
||||
if (E == nullptr)
|
||||
return nullptr;
|
||||
@@ -4124,8 +4141,9 @@ Node *AbstractManglingParser<Derived, Alloc>::parsePrefixExpr(StringView Kind,
|
||||
}
|
||||
|
||||
template <typename Derived, typename Alloc>
|
||||
Node *AbstractManglingParser<Derived, Alloc>::parseBinaryExpr(StringView Kind,
|
||||
Node::Prec Prec) {
|
||||
Node *
|
||||
AbstractManglingParser<Derived, Alloc>::parseBinaryExpr(std::string_view Kind,
|
||||
Node::Prec Prec) {
|
||||
Node *LHS = getDerived().parseExpr();
|
||||
if (LHS == nullptr)
|
||||
return nullptr;
|
||||
@@ -4136,9 +4154,9 @@ Node *AbstractManglingParser<Derived, Alloc>::parseBinaryExpr(StringView Kind,
|
||||
}
|
||||
|
||||
template <typename Derived, typename Alloc>
|
||||
Node *
|
||||
AbstractManglingParser<Derived, Alloc>::parseIntegerLiteral(StringView Lit) {
|
||||
StringView Tmp = parseNumber(true);
|
||||
Node *AbstractManglingParser<Derived, Alloc>::parseIntegerLiteral(
|
||||
std::string_view Lit) {
|
||||
std::string_view Tmp = parseNumber(true);
|
||||
if (!Tmp.empty() && consumeIf('E'))
|
||||
return make<IntegerLiteral>(Lit, Tmp);
|
||||
return nullptr;
|
||||
@@ -4168,7 +4186,7 @@ Node *AbstractManglingParser<Derived, Alloc>::parseFunctionParam() {
|
||||
return make<NameType>("this");
|
||||
if (consumeIf("fp")) {
|
||||
parseCVQualifiers();
|
||||
StringView Num = parseNumber();
|
||||
std::string_view Num = parseNumber();
|
||||
if (!consumeIf('_'))
|
||||
return nullptr;
|
||||
return make<FunctionParam>(Num);
|
||||
@@ -4179,7 +4197,7 @@ Node *AbstractManglingParser<Derived, Alloc>::parseFunctionParam() {
|
||||
if (!consumeIf('p'))
|
||||
return nullptr;
|
||||
parseCVQualifiers();
|
||||
StringView Num = parseNumber();
|
||||
std::string_view Num = parseNumber();
|
||||
if (!consumeIf('_'))
|
||||
return nullptr;
|
||||
return make<FunctionParam>(Num);
|
||||
@@ -4333,7 +4351,7 @@ Node *AbstractManglingParser<Derived, Alloc>::parseExprPrimary() {
|
||||
Node *T = getDerived().parseType();
|
||||
if (T == nullptr)
|
||||
return nullptr;
|
||||
StringView N = parseNumber(/*AllowNegative=*/true);
|
||||
std::string_view N = parseNumber(/*AllowNegative=*/true);
|
||||
if (N.empty())
|
||||
return nullptr;
|
||||
if (!consumeIf('E'))
|
||||
@@ -4456,7 +4474,7 @@ AbstractManglingParser<Derived, Alloc>::parsePointerToMemberConversionExpr(
|
||||
Node *Expr = getDerived().parseExpr();
|
||||
if (!Expr)
|
||||
return nullptr;
|
||||
StringView Offset = getDerived().parseNumber(true);
|
||||
std::string_view Offset = getDerived().parseNumber(true);
|
||||
if (!consumeIf('E'))
|
||||
return nullptr;
|
||||
return make<PointerToMemberConversionExpr>(Ty, Expr, Offset, Prec);
|
||||
@@ -4474,7 +4492,7 @@ Node *AbstractManglingParser<Derived, Alloc>::parseSubobjectExpr() {
|
||||
Node *Expr = getDerived().parseExpr();
|
||||
if (!Expr)
|
||||
return nullptr;
|
||||
StringView Offset = getDerived().parseNumber(true);
|
||||
std::string_view Offset = getDerived().parseNumber(true);
|
||||
size_t SelectorsBegin = Names.size();
|
||||
while (consumeIf('_')) {
|
||||
Node *Selector = make<NameType>(parseNumber());
|
||||
@@ -5111,7 +5129,7 @@ template <>
|
||||
struct FloatData<long double>
|
||||
{
|
||||
#if defined(__mips__) && defined(__mips_n64) || defined(__aarch64__) || \
|
||||
defined(__wasm__) || defined(__riscv)
|
||||
defined(__wasm__) || defined(__riscv) || defined(__loongarch__)
|
||||
static const size_t mangled_size = 32;
|
||||
#elif defined(__arm__) || defined(__mips__) || defined(__hexagon__)
|
||||
static const size_t mangled_size = 16;
|
||||
@@ -5133,7 +5151,7 @@ Node *AbstractManglingParser<Alloc, Derived>::parseFloatingLiteral() {
|
||||
const size_t N = FloatData<Float>::mangled_size;
|
||||
if (numLeft() <= N)
|
||||
return nullptr;
|
||||
StringView Data(First, First + N);
|
||||
std::string_view Data(First, N);
|
||||
for (char C : Data)
|
||||
if (!std::isxdigit(C))
|
||||
return nullptr;
|
||||
@@ -5453,7 +5471,8 @@ Node *AbstractManglingParser<Derived, Alloc>::parse() {
|
||||
if (Encoding == nullptr)
|
||||
return nullptr;
|
||||
if (look() == '.') {
|
||||
Encoding = make<DotSuffix>(Encoding, StringView(First, Last));
|
||||
Encoding =
|
||||
make<DotSuffix>(Encoding, std::string_view(First, Last - First));
|
||||
First = Last;
|
||||
}
|
||||
if (numLeft() != 0)
|
||||
@@ -5489,4 +5508,4 @@ struct ManglingParser : AbstractManglingParser<ManglingParser<Alloc>, Alloc> {
|
||||
|
||||
DEMANGLE_NAMESPACE_END
|
||||
|
||||
#endif // LLVM_DEMANGLE_ITANIUMDEMANGLE_H
|
||||
#endif // DEMANGLE_ITANIUMDEMANGLE_H
|
||||
|
||||
@@ -10,8 +10,9 @@
|
||||
#define LLVM_DEMANGLE_MICROSOFTDEMANGLE_H
|
||||
|
||||
#include "llvm/Demangle/MicrosoftDemangleNodes.h"
|
||||
#include "llvm/Demangle/StringView.h"
|
||||
|
||||
#include <cassert>
|
||||
#include <string_view>
|
||||
#include <utility>
|
||||
|
||||
namespace llvm {
|
||||
@@ -100,7 +101,7 @@ public:
|
||||
if (Head->Used <= Head->Capacity)
|
||||
return new (PP) T(std::forward<Args>(ConstructorArgs)...);
|
||||
|
||||
static_assert(Size < AllocUnit, "");
|
||||
static_assert(Size < AllocUnit);
|
||||
addNode(AllocUnit);
|
||||
Head->Used = Size;
|
||||
return new (Head->Buf) T(std::forward<Args>(ConstructorArgs)...);
|
||||
@@ -142,9 +143,9 @@ public:
|
||||
|
||||
// You are supposed to call parse() first and then check if error is true. If
|
||||
// it is false, call output() to write the formatted name to the given stream.
|
||||
SymbolNode *parse(StringView &MangledName);
|
||||
SymbolNode *parse(std::string_view &MangledName);
|
||||
|
||||
TagTypeNode *parseTagUniqueName(StringView &MangledName);
|
||||
TagTypeNode *parseTagUniqueName(std::string_view &MangledName);
|
||||
|
||||
// True if an error occurred.
|
||||
bool Error = false;
|
||||
@@ -152,104 +153,112 @@ public:
|
||||
void dumpBackReferences();
|
||||
|
||||
private:
|
||||
SymbolNode *demangleEncodedSymbol(StringView &MangledName,
|
||||
SymbolNode *demangleEncodedSymbol(std::string_view &MangledName,
|
||||
QualifiedNameNode *QN);
|
||||
SymbolNode *demangleDeclarator(StringView &MangledName);
|
||||
SymbolNode *demangleMD5Name(StringView &MangledName);
|
||||
SymbolNode *demangleTypeinfoName(StringView &MangledName);
|
||||
SymbolNode *demangleDeclarator(std::string_view &MangledName);
|
||||
SymbolNode *demangleMD5Name(std::string_view &MangledName);
|
||||
SymbolNode *demangleTypeinfoName(std::string_view &MangledName);
|
||||
|
||||
VariableSymbolNode *demangleVariableEncoding(StringView &MangledName,
|
||||
VariableSymbolNode *demangleVariableEncoding(std::string_view &MangledName,
|
||||
StorageClass SC);
|
||||
FunctionSymbolNode *demangleFunctionEncoding(StringView &MangledName);
|
||||
FunctionSymbolNode *demangleFunctionEncoding(std::string_view &MangledName);
|
||||
|
||||
Qualifiers demanglePointerExtQualifiers(StringView &MangledName);
|
||||
Qualifiers demanglePointerExtQualifiers(std::string_view &MangledName);
|
||||
|
||||
// Parser functions. This is a recursive-descent parser.
|
||||
TypeNode *demangleType(StringView &MangledName, QualifierMangleMode QMM);
|
||||
PrimitiveTypeNode *demanglePrimitiveType(StringView &MangledName);
|
||||
CustomTypeNode *demangleCustomType(StringView &MangledName);
|
||||
TagTypeNode *demangleClassType(StringView &MangledName);
|
||||
PointerTypeNode *demanglePointerType(StringView &MangledName);
|
||||
PointerTypeNode *demangleMemberPointerType(StringView &MangledName);
|
||||
FunctionSignatureNode *demangleFunctionType(StringView &MangledName,
|
||||
TypeNode *demangleType(std::string_view &MangledName,
|
||||
QualifierMangleMode QMM);
|
||||
PrimitiveTypeNode *demanglePrimitiveType(std::string_view &MangledName);
|
||||
CustomTypeNode *demangleCustomType(std::string_view &MangledName);
|
||||
TagTypeNode *demangleClassType(std::string_view &MangledName);
|
||||
PointerTypeNode *demanglePointerType(std::string_view &MangledName);
|
||||
PointerTypeNode *demangleMemberPointerType(std::string_view &MangledName);
|
||||
FunctionSignatureNode *demangleFunctionType(std::string_view &MangledName,
|
||||
bool HasThisQuals);
|
||||
|
||||
ArrayTypeNode *demangleArrayType(StringView &MangledName);
|
||||
ArrayTypeNode *demangleArrayType(std::string_view &MangledName);
|
||||
|
||||
NodeArrayNode *demangleFunctionParameterList(StringView &MangledName,
|
||||
NodeArrayNode *demangleFunctionParameterList(std::string_view &MangledName,
|
||||
bool &IsVariadic);
|
||||
NodeArrayNode *demangleTemplateParameterList(StringView &MangledName);
|
||||
NodeArrayNode *demangleTemplateParameterList(std::string_view &MangledName);
|
||||
|
||||
std::pair<uint64_t, bool> demangleNumber(StringView &MangledName);
|
||||
uint64_t demangleUnsigned(StringView &MangledName);
|
||||
int64_t demangleSigned(StringView &MangledName);
|
||||
std::pair<uint64_t, bool> demangleNumber(std::string_view &MangledName);
|
||||
uint64_t demangleUnsigned(std::string_view &MangledName);
|
||||
int64_t demangleSigned(std::string_view &MangledName);
|
||||
|
||||
void memorizeString(StringView s);
|
||||
void memorizeString(std::string_view s);
|
||||
void memorizeIdentifier(IdentifierNode *Identifier);
|
||||
|
||||
/// Allocate a copy of \p Borrowed into memory that we own.
|
||||
StringView copyString(StringView Borrowed);
|
||||
std::string_view copyString(std::string_view Borrowed);
|
||||
|
||||
QualifiedNameNode *demangleFullyQualifiedTypeName(StringView &MangledName);
|
||||
QualifiedNameNode *demangleFullyQualifiedSymbolName(StringView &MangledName);
|
||||
QualifiedNameNode *
|
||||
demangleFullyQualifiedTypeName(std::string_view &MangledName);
|
||||
QualifiedNameNode *
|
||||
demangleFullyQualifiedSymbolName(std::string_view &MangledName);
|
||||
|
||||
IdentifierNode *demangleUnqualifiedTypeName(StringView &MangledName,
|
||||
IdentifierNode *demangleUnqualifiedTypeName(std::string_view &MangledName,
|
||||
bool Memorize);
|
||||
IdentifierNode *demangleUnqualifiedSymbolName(StringView &MangledName,
|
||||
IdentifierNode *demangleUnqualifiedSymbolName(std::string_view &MangledName,
|
||||
NameBackrefBehavior NBB);
|
||||
|
||||
QualifiedNameNode *demangleNameScopeChain(StringView &MangledName,
|
||||
QualifiedNameNode *demangleNameScopeChain(std::string_view &MangledName,
|
||||
IdentifierNode *UnqualifiedName);
|
||||
IdentifierNode *demangleNameScopePiece(StringView &MangledName);
|
||||
IdentifierNode *demangleNameScopePiece(std::string_view &MangledName);
|
||||
|
||||
NamedIdentifierNode *demangleBackRefName(StringView &MangledName);
|
||||
IdentifierNode *demangleTemplateInstantiationName(StringView &MangledName,
|
||||
NameBackrefBehavior NBB);
|
||||
NamedIdentifierNode *demangleBackRefName(std::string_view &MangledName);
|
||||
IdentifierNode *
|
||||
demangleTemplateInstantiationName(std::string_view &MangledName,
|
||||
NameBackrefBehavior NBB);
|
||||
IntrinsicFunctionKind
|
||||
translateIntrinsicFunctionCode(char CH, FunctionIdentifierCodeGroup Group);
|
||||
IdentifierNode *demangleFunctionIdentifierCode(StringView &MangledName);
|
||||
IdentifierNode *demangleFunctionIdentifierCode(std::string_view &MangledName);
|
||||
IdentifierNode *
|
||||
demangleFunctionIdentifierCode(StringView &MangledName,
|
||||
demangleFunctionIdentifierCode(std::string_view &MangledName,
|
||||
FunctionIdentifierCodeGroup Group);
|
||||
StructorIdentifierNode *demangleStructorIdentifier(StringView &MangledName,
|
||||
bool IsDestructor);
|
||||
StructorIdentifierNode *
|
||||
demangleStructorIdentifier(std::string_view &MangledName, bool IsDestructor);
|
||||
ConversionOperatorIdentifierNode *
|
||||
demangleConversionOperatorIdentifier(StringView &MangledName);
|
||||
demangleConversionOperatorIdentifier(std::string_view &MangledName);
|
||||
LiteralOperatorIdentifierNode *
|
||||
demangleLiteralOperatorIdentifier(StringView &MangledName);
|
||||
demangleLiteralOperatorIdentifier(std::string_view &MangledName);
|
||||
|
||||
SymbolNode *demangleSpecialIntrinsic(StringView &MangledName);
|
||||
SymbolNode *demangleSpecialIntrinsic(std::string_view &MangledName);
|
||||
SpecialTableSymbolNode *
|
||||
demangleSpecialTableSymbolNode(StringView &MangledName,
|
||||
demangleSpecialTableSymbolNode(std::string_view &MangledName,
|
||||
SpecialIntrinsicKind SIK);
|
||||
LocalStaticGuardVariableNode *
|
||||
demangleLocalStaticGuard(StringView &MangledName, bool IsThread);
|
||||
demangleLocalStaticGuard(std::string_view &MangledName, bool IsThread);
|
||||
VariableSymbolNode *demangleUntypedVariable(ArenaAllocator &Arena,
|
||||
StringView &MangledName,
|
||||
StringView VariableName);
|
||||
std::string_view &MangledName,
|
||||
std::string_view VariableName);
|
||||
VariableSymbolNode *
|
||||
demangleRttiBaseClassDescriptorNode(ArenaAllocator &Arena,
|
||||
StringView &MangledName);
|
||||
FunctionSymbolNode *demangleInitFiniStub(StringView &MangledName,
|
||||
std::string_view &MangledName);
|
||||
FunctionSymbolNode *demangleInitFiniStub(std::string_view &MangledName,
|
||||
bool IsDestructor);
|
||||
|
||||
NamedIdentifierNode *demangleSimpleName(StringView &MangledName,
|
||||
NamedIdentifierNode *demangleSimpleName(std::string_view &MangledName,
|
||||
bool Memorize);
|
||||
NamedIdentifierNode *demangleAnonymousNamespaceName(StringView &MangledName);
|
||||
NamedIdentifierNode *demangleLocallyScopedNamePiece(StringView &MangledName);
|
||||
EncodedStringLiteralNode *demangleStringLiteral(StringView &MangledName);
|
||||
FunctionSymbolNode *demangleVcallThunkNode(StringView &MangledName);
|
||||
NamedIdentifierNode *
|
||||
demangleAnonymousNamespaceName(std::string_view &MangledName);
|
||||
NamedIdentifierNode *
|
||||
demangleLocallyScopedNamePiece(std::string_view &MangledName);
|
||||
EncodedStringLiteralNode *
|
||||
demangleStringLiteral(std::string_view &MangledName);
|
||||
FunctionSymbolNode *demangleVcallThunkNode(std::string_view &MangledName);
|
||||
|
||||
StringView demangleSimpleString(StringView &MangledName, bool Memorize);
|
||||
std::string_view demangleSimpleString(std::string_view &MangledName,
|
||||
bool Memorize);
|
||||
|
||||
FuncClass demangleFunctionClass(StringView &MangledName);
|
||||
CallingConv demangleCallingConvention(StringView &MangledName);
|
||||
StorageClass demangleVariableStorageClass(StringView &MangledName);
|
||||
bool demangleThrowSpecification(StringView &MangledName);
|
||||
wchar_t demangleWcharLiteral(StringView &MangledName);
|
||||
uint8_t demangleCharLiteral(StringView &MangledName);
|
||||
FuncClass demangleFunctionClass(std::string_view &MangledName);
|
||||
CallingConv demangleCallingConvention(std::string_view &MangledName);
|
||||
StorageClass demangleVariableStorageClass(std::string_view &MangledName);
|
||||
bool demangleThrowSpecification(std::string_view &MangledName);
|
||||
wchar_t demangleWcharLiteral(std::string_view &MangledName);
|
||||
uint8_t demangleCharLiteral(std::string_view &MangledName);
|
||||
|
||||
std::pair<Qualifiers, bool> demangleQualifiers(StringView &MangledName);
|
||||
std::pair<Qualifiers, bool> demangleQualifiers(std::string_view &MangledName);
|
||||
|
||||
// Memory allocator.
|
||||
ArenaAllocator Arena;
|
||||
|
||||
@@ -13,10 +13,10 @@
|
||||
#ifndef LLVM_DEMANGLE_MICROSOFTDEMANGLENODES_H
|
||||
#define LLVM_DEMANGLE_MICROSOFTDEMANGLENODES_H
|
||||
|
||||
#include "llvm/Demangle/StringView.h"
|
||||
#include <array>
|
||||
#include <cstdint>
|
||||
#include <string>
|
||||
#include <string_view>
|
||||
|
||||
namespace llvm {
|
||||
namespace itanium_demangle {
|
||||
@@ -25,7 +25,6 @@ class OutputBuffer;
|
||||
}
|
||||
|
||||
using llvm::itanium_demangle::OutputBuffer;
|
||||
using llvm::itanium_demangle::StringView;
|
||||
|
||||
namespace llvm {
|
||||
namespace ms_demangle {
|
||||
@@ -384,7 +383,7 @@ struct NamedIdentifierNode : public IdentifierNode {
|
||||
|
||||
void output(OutputBuffer &OB, OutputFlags Flags) const override;
|
||||
|
||||
StringView Name;
|
||||
std::string_view Name;
|
||||
};
|
||||
|
||||
struct IntrinsicFunctionIdentifierNode : public IdentifierNode {
|
||||
@@ -403,7 +402,7 @@ struct LiteralOperatorIdentifierNode : public IdentifierNode {
|
||||
|
||||
void output(OutputBuffer &OB, OutputFlags Flags) const override;
|
||||
|
||||
StringView Name;
|
||||
std::string_view Name;
|
||||
};
|
||||
|
||||
struct LocalStaticGuardIdentifierNode : public IdentifierNode {
|
||||
@@ -516,7 +515,8 @@ struct NodeArrayNode : public Node {
|
||||
|
||||
void output(OutputBuffer &OB, OutputFlags Flags) const override;
|
||||
|
||||
void output(OutputBuffer &OB, OutputFlags Flags, StringView Separator) const;
|
||||
void output(OutputBuffer &OB, OutputFlags Flags,
|
||||
std::string_view Separator) const;
|
||||
|
||||
Node **Nodes = nullptr;
|
||||
size_t Count = 0;
|
||||
@@ -601,7 +601,7 @@ struct EncodedStringLiteralNode : public SymbolNode {
|
||||
|
||||
void output(OutputBuffer &OB, OutputFlags Flags) const override;
|
||||
|
||||
StringView DecodedString;
|
||||
std::string_view DecodedString;
|
||||
bool IsTruncated = false;
|
||||
CharKind Char = CharKind::Char;
|
||||
};
|
||||
|
||||
@@ -1,122 +0,0 @@
|
||||
//===--- StringView.h ----------------*- mode:c++;eval:(read-only-mode) -*-===//
|
||||
// Do not edit! See README.txt.
|
||||
// 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
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// FIXME: Use std::string_view instead when we support C++17.
|
||||
// There are two copies of this file in the source tree. The one under
|
||||
// libcxxabi is the original and the one under llvm is the copy. Use
|
||||
// cp-to-llvm.sh to update the copy. See README.txt for more details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_DEMANGLE_STRINGVIEW_H
|
||||
#define LLVM_DEMANGLE_STRINGVIEW_H
|
||||
|
||||
#include "DemangleConfig.h"
|
||||
#include <cassert>
|
||||
#include <cstring>
|
||||
|
||||
DEMANGLE_NAMESPACE_BEGIN
|
||||
|
||||
class StringView {
|
||||
const char *First;
|
||||
const char *Last;
|
||||
|
||||
public:
|
||||
static const size_t npos = ~size_t(0);
|
||||
|
||||
template <size_t N>
|
||||
StringView(const char (&Str)[N]) : First(Str), Last(Str + N - 1) {}
|
||||
StringView(const char *First_, const char *Last_)
|
||||
: First(First_), Last(Last_) {}
|
||||
StringView(const char *First_, size_t Len)
|
||||
: First(First_), Last(First_ + Len) {}
|
||||
StringView(const char *Str) : First(Str), Last(Str + std::strlen(Str)) {}
|
||||
StringView() : First(nullptr), Last(nullptr) {}
|
||||
|
||||
StringView substr(size_t Pos, size_t Len = npos) const {
|
||||
assert(Pos <= size());
|
||||
if (Len > size() - Pos)
|
||||
Len = size() - Pos;
|
||||
return StringView(begin() + Pos, Len);
|
||||
}
|
||||
|
||||
size_t find(char C, size_t From = 0) const {
|
||||
// Avoid calling memchr with nullptr.
|
||||
if (From < size()) {
|
||||
// Just forward to memchr, which is faster than a hand-rolled loop.
|
||||
if (const void *P = ::memchr(First + From, C, size() - From))
|
||||
return size_t(static_cast<const char *>(P) - First);
|
||||
}
|
||||
return npos;
|
||||
}
|
||||
|
||||
StringView dropFront(size_t N = 1) const {
|
||||
if (N >= size())
|
||||
N = size();
|
||||
return StringView(First + N, Last);
|
||||
}
|
||||
|
||||
StringView dropBack(size_t N = 1) const {
|
||||
if (N >= size())
|
||||
N = size();
|
||||
return StringView(First, Last - N);
|
||||
}
|
||||
|
||||
char front() const {
|
||||
assert(!empty());
|
||||
return *begin();
|
||||
}
|
||||
|
||||
char back() const {
|
||||
assert(!empty());
|
||||
return *(end() - 1);
|
||||
}
|
||||
|
||||
char popFront() {
|
||||
assert(!empty());
|
||||
return *First++;
|
||||
}
|
||||
|
||||
bool consumeFront(char C) {
|
||||
if (!startsWith(C))
|
||||
return false;
|
||||
*this = dropFront(1);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool consumeFront(StringView S) {
|
||||
if (!startsWith(S))
|
||||
return false;
|
||||
*this = dropFront(S.size());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool startsWith(char C) const { return !empty() && *begin() == C; }
|
||||
|
||||
bool startsWith(StringView Str) const {
|
||||
if (Str.size() > size())
|
||||
return false;
|
||||
return std::strncmp(Str.begin(), begin(), Str.size()) == 0;
|
||||
}
|
||||
|
||||
const char &operator[](size_t Idx) const { return *(begin() + Idx); }
|
||||
|
||||
const char *begin() const { return First; }
|
||||
const char *end() const { return Last; }
|
||||
size_t size() const { return static_cast<size_t>(Last - First); }
|
||||
bool empty() const { return First == Last; }
|
||||
};
|
||||
|
||||
inline bool operator==(const StringView &LHS, const StringView &RHS) {
|
||||
return LHS.size() == RHS.size() &&
|
||||
std::strncmp(LHS.begin(), RHS.begin(), LHS.size()) == 0;
|
||||
}
|
||||
|
||||
DEMANGLE_NAMESPACE_END
|
||||
|
||||
#endif
|
||||
38
lib/external/llvm-demangle/include/llvm/Demangle/StringViewExtras.h
vendored
Normal file
38
lib/external/llvm-demangle/include/llvm/Demangle/StringViewExtras.h
vendored
Normal file
@@ -0,0 +1,38 @@
|
||||
//===--- StringViewExtras.h ----------*- mode:c++;eval:(read-only-mode) -*-===//
|
||||
// Do not edit! See README.txt.
|
||||
// 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
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// There are two copies of this file in the source tree. The one under
|
||||
// libcxxabi is the original and the one under llvm is the copy. Use
|
||||
// cp-to-llvm.sh to update the copy. See README.txt for more details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef DEMANGLE_STRINGVIEW_H
|
||||
#define DEMANGLE_STRINGVIEW_H
|
||||
|
||||
#include "DemangleConfig.h"
|
||||
|
||||
#include <string_view>
|
||||
|
||||
DEMANGLE_NAMESPACE_BEGIN
|
||||
|
||||
inline bool starts_with(std::string_view self, char C) noexcept {
|
||||
return !self.empty() && *self.begin() == C;
|
||||
}
|
||||
|
||||
inline bool starts_with(std::string_view haystack,
|
||||
std::string_view needle) noexcept {
|
||||
if (needle.size() > haystack.size())
|
||||
return false;
|
||||
haystack.remove_suffix(haystack.size() - needle.size());
|
||||
return haystack == needle;
|
||||
}
|
||||
|
||||
DEMANGLE_NAMESPACE_END
|
||||
|
||||
#endif
|
||||
@@ -13,16 +13,19 @@
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_DEMANGLE_UTILITY_H
|
||||
#define LLVM_DEMANGLE_UTILITY_H
|
||||
#ifndef DEMANGLE_UTILITY_H
|
||||
#define DEMANGLE_UTILITY_H
|
||||
|
||||
#include "DemangleConfig.h"
|
||||
|
||||
#include "StringView.h"
|
||||
#include <array>
|
||||
#include <cassert>
|
||||
#include <cstdint>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <exception>
|
||||
#include <limits>
|
||||
#include <string_view>
|
||||
|
||||
DEMANGLE_NAMESPACE_BEGIN
|
||||
|
||||
@@ -64,23 +67,22 @@ class OutputBuffer {
|
||||
if (isNeg)
|
||||
*--TempPtr = '-';
|
||||
|
||||
return operator+=(StringView(TempPtr, Temp.data() + Temp.size()));
|
||||
return operator+=(
|
||||
std::string_view(TempPtr, Temp.data() + Temp.size() - TempPtr));
|
||||
}
|
||||
|
||||
public:
|
||||
OutputBuffer(char *StartBuf, size_t Size)
|
||||
: Buffer(StartBuf), CurrentPosition(0), BufferCapacity(Size) {}
|
||||
: Buffer(StartBuf), BufferCapacity(Size) {}
|
||||
OutputBuffer(char *StartBuf, size_t *SizePtr)
|
||||
: OutputBuffer(StartBuf, StartBuf ? *SizePtr : 0) {}
|
||||
OutputBuffer() = default;
|
||||
// Non-copyable
|
||||
OutputBuffer(const OutputBuffer &) = delete;
|
||||
OutputBuffer &operator=(const OutputBuffer &) = delete;
|
||||
|
||||
operator StringView() const { return StringView(Buffer, CurrentPosition); }
|
||||
|
||||
void reset(char *Buffer_, size_t BufferCapacity_) {
|
||||
CurrentPosition = 0;
|
||||
Buffer = Buffer_;
|
||||
BufferCapacity = BufferCapacity_;
|
||||
operator std::string_view() const {
|
||||
return std::string_view(Buffer, CurrentPosition);
|
||||
}
|
||||
|
||||
/// If a ParameterPackExpansion (or similar type) is encountered, the offset
|
||||
@@ -103,10 +105,10 @@ public:
|
||||
*this += Close;
|
||||
}
|
||||
|
||||
OutputBuffer &operator+=(StringView R) {
|
||||
OutputBuffer &operator+=(std::string_view R) {
|
||||
if (size_t Size = R.size()) {
|
||||
grow(Size);
|
||||
std::memcpy(Buffer + CurrentPosition, R.begin(), Size);
|
||||
std::memcpy(Buffer + CurrentPosition, &*R.begin(), Size);
|
||||
CurrentPosition += Size;
|
||||
}
|
||||
return *this;
|
||||
@@ -118,18 +120,18 @@ public:
|
||||
return *this;
|
||||
}
|
||||
|
||||
OutputBuffer &prepend(StringView R) {
|
||||
OutputBuffer &prepend(std::string_view R) {
|
||||
size_t Size = R.size();
|
||||
|
||||
grow(Size);
|
||||
std::memmove(Buffer + Size, Buffer, CurrentPosition);
|
||||
std::memcpy(Buffer, R.begin(), Size);
|
||||
std::memcpy(Buffer, &*R.begin(), Size);
|
||||
CurrentPosition += Size;
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
OutputBuffer &operator<<(StringView R) { return (*this += R); }
|
||||
OutputBuffer &operator<<(std::string_view R) { return (*this += R); }
|
||||
|
||||
OutputBuffer &operator<<(char C) { return (*this += C); }
|
||||
|
||||
@@ -198,21 +200,6 @@ public:
|
||||
ScopedOverride &operator=(const ScopedOverride &) = delete;
|
||||
};
|
||||
|
||||
inline bool initializeOutputBuffer(char *Buf, size_t *N, OutputBuffer &OB,
|
||||
size_t InitSize) {
|
||||
size_t BufferSize;
|
||||
if (Buf == nullptr) {
|
||||
Buf = static_cast<char *>(std::malloc(InitSize));
|
||||
if (Buf == nullptr)
|
||||
return false;
|
||||
BufferSize = InitSize;
|
||||
} else
|
||||
BufferSize = *N;
|
||||
|
||||
OB.reset(Buf, BufferSize);
|
||||
return true;
|
||||
}
|
||||
|
||||
DEMANGLE_NAMESPACE_END
|
||||
|
||||
#endif
|
||||
|
||||
382
lib/external/llvm-demangle/source/DLangDemangle.cpp
vendored
382
lib/external/llvm-demangle/source/DLangDemangle.cpp
vendored
@@ -14,16 +14,17 @@
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/Demangle/Demangle.h"
|
||||
#include "llvm/Demangle/StringView.h"
|
||||
#include "llvm/Demangle/StringViewExtras.h"
|
||||
#include "llvm/Demangle/Utility.h"
|
||||
|
||||
#include <cctype>
|
||||
#include <cstring>
|
||||
#include <limits>
|
||||
#include <string_view>
|
||||
|
||||
using namespace llvm;
|
||||
using llvm::itanium_demangle::OutputBuffer;
|
||||
using llvm::itanium_demangle::StringView;
|
||||
using llvm::itanium_demangle::starts_with;
|
||||
|
||||
namespace {
|
||||
|
||||
@@ -32,7 +33,7 @@ struct Demangler {
|
||||
/// Initialize the information structure we use to pass around information.
|
||||
///
|
||||
/// \param Mangled String to demangle.
|
||||
Demangler(const char *Mangled);
|
||||
Demangler(std::string_view Mangled);
|
||||
|
||||
/// Extract and demangle the mangled symbol and append it to the output
|
||||
/// string.
|
||||
@@ -52,46 +53,42 @@ private:
|
||||
/// \param Demangled output buffer to write the demangled name.
|
||||
/// \param Mangled mangled symbol to be demangled.
|
||||
///
|
||||
/// \return The remaining string on success or nullptr on failure.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#name_mangling .
|
||||
/// \see https://dlang.org/spec/abi.html#MangledName .
|
||||
const char *parseMangle(OutputBuffer *Demangled, const char *Mangled);
|
||||
void parseMangle(OutputBuffer *Demangled, std::string_view &Mangled);
|
||||
|
||||
/// Extract the number from a given string.
|
||||
///
|
||||
/// \param Mangled string to extract the number.
|
||||
/// \param Ret assigned result value.
|
||||
///
|
||||
/// \return The remaining string on success or nullptr on failure.
|
||||
///
|
||||
/// \note A result larger than UINT_MAX is considered a failure.
|
||||
/// \note Ret larger than UINT_MAX is considered a failure.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#Number .
|
||||
const char *decodeNumber(const char *Mangled, unsigned long &Ret);
|
||||
void decodeNumber(std::string_view &Mangled, unsigned long &Ret);
|
||||
|
||||
/// Extract the back reference position from a given string.
|
||||
///
|
||||
/// \param Mangled string to extract the back reference position.
|
||||
/// \param Ret assigned result value.
|
||||
///
|
||||
/// \return the remaining string on success or nullptr on failure.
|
||||
/// \return true on success, false on error.
|
||||
///
|
||||
/// \note Ret is always >= 0 on success, and unspecified on failure
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#back_ref .
|
||||
/// \see https://dlang.org/spec/abi.html#NumberBackRef .
|
||||
const char *decodeBackrefPos(const char *Mangled, long &Ret);
|
||||
bool decodeBackrefPos(std::string_view &Mangled, long &Ret);
|
||||
|
||||
/// Extract the symbol pointed by the back reference form a given string.
|
||||
///
|
||||
/// \param Mangled string to extract the back reference position.
|
||||
/// \param Ret assigned result value.
|
||||
///
|
||||
/// \return the remaining string on success or nullptr on failure.
|
||||
/// \return true on success, false on error.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#back_ref .
|
||||
const char *decodeBackref(const char *Mangled, const char *&Ret);
|
||||
bool decodeBackref(std::string_view &Mangled, std::string_view &Ret);
|
||||
|
||||
/// Extract and demangle backreferenced symbol from a given mangled symbol
|
||||
/// and append it to the output string.
|
||||
@@ -99,22 +96,18 @@ private:
|
||||
/// \param Demangled output buffer to write the demangled name.
|
||||
/// \param Mangled mangled symbol to be demangled.
|
||||
///
|
||||
/// \return the remaining string on success or nullptr on failure.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#back_ref .
|
||||
/// \see https://dlang.org/spec/abi.html#IdentifierBackRef .
|
||||
const char *parseSymbolBackref(OutputBuffer *Demangled, const char *Mangled);
|
||||
void parseSymbolBackref(OutputBuffer *Demangled, std::string_view &Mangled);
|
||||
|
||||
/// Extract and demangle backreferenced type from a given mangled symbol
|
||||
/// and append it to the output string.
|
||||
///
|
||||
/// \param Mangled mangled symbol to be demangled.
|
||||
///
|
||||
/// \return the remaining string on success or nullptr on failure.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#back_ref .
|
||||
/// \see https://dlang.org/spec/abi.html#TypeBackRef .
|
||||
const char *parseTypeBackref(const char *Mangled);
|
||||
void parseTypeBackref(std::string_view &Mangled);
|
||||
|
||||
/// Check whether it is the beginning of a symbol name.
|
||||
///
|
||||
@@ -123,7 +116,7 @@ private:
|
||||
/// \return true on success, false otherwise.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#SymbolName .
|
||||
bool isSymbolName(const char *Mangled);
|
||||
bool isSymbolName(std::string_view Mangled);
|
||||
|
||||
/// Extract and demangle an identifier from a given mangled symbol append it
|
||||
/// to the output string.
|
||||
@@ -131,10 +124,8 @@ private:
|
||||
/// \param Demangled Output buffer to write the demangled name.
|
||||
/// \param Mangled Mangled symbol to be demangled.
|
||||
///
|
||||
/// \return The remaining string on success or nullptr on failure.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#SymbolName .
|
||||
const char *parseIdentifier(OutputBuffer *Demangled, const char *Mangled);
|
||||
void parseIdentifier(OutputBuffer *Demangled, std::string_view &Mangled);
|
||||
|
||||
/// Extract and demangle the plain identifier from a given mangled symbol and
|
||||
/// prepend/append it to the output string, with a special treatment for some
|
||||
@@ -144,11 +135,9 @@ private:
|
||||
/// \param Mangled Mangled symbol to be demangled.
|
||||
/// \param Len Length of the mangled symbol name.
|
||||
///
|
||||
/// \return The remaining string on success or nullptr on failure.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#LName .
|
||||
const char *parseLName(OutputBuffer *Demangled, const char *Mangled,
|
||||
unsigned long Len);
|
||||
void parseLName(OutputBuffer *Demangled, std::string_view &Mangled,
|
||||
unsigned long Len);
|
||||
|
||||
/// Extract and demangle the qualified symbol from a given mangled symbol
|
||||
/// append it to the output string.
|
||||
@@ -156,33 +145,38 @@ private:
|
||||
/// \param Demangled Output buffer to write the demangled name.
|
||||
/// \param Mangled Mangled symbol to be demangled.
|
||||
///
|
||||
/// \return The remaining string on success or nullptr on failure.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#QualifiedName .
|
||||
const char *parseQualified(OutputBuffer *Demangled, const char *Mangled);
|
||||
void parseQualified(OutputBuffer *Demangled, std::string_view &Mangled);
|
||||
|
||||
/// Extract and demangle a type from a given mangled symbol append it to
|
||||
/// the output string.
|
||||
///
|
||||
/// \param Mangled mangled symbol to be demangled.
|
||||
///
|
||||
/// \return the remaining string on success or nullptr on failure.
|
||||
/// \return true on success, false on error.
|
||||
///
|
||||
/// \see https://dlang.org/spec/abi.html#Type .
|
||||
const char *parseType(const char *Mangled);
|
||||
bool parseType(std::string_view &Mangled);
|
||||
|
||||
/// The string we are demangling.
|
||||
const char *Str;
|
||||
/// An immutable view of the string we are demangling.
|
||||
const std::string_view Str;
|
||||
/// The index of the last back reference.
|
||||
int LastBackref;
|
||||
};
|
||||
|
||||
} // namespace
|
||||
|
||||
const char *Demangler::decodeNumber(const char *Mangled, unsigned long &Ret) {
|
||||
// Return nullptr if trying to extract something that isn't a digit.
|
||||
if (Mangled == nullptr || !std::isdigit(*Mangled))
|
||||
return nullptr;
|
||||
void Demangler::decodeNumber(std::string_view &Mangled, unsigned long &Ret) {
|
||||
// Clear Mangled if trying to extract something that isn't a digit.
|
||||
if (Mangled.empty()) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
if (!std::isdigit(Mangled.front())) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
unsigned long Val = 0;
|
||||
|
||||
@@ -190,25 +184,29 @@ const char *Demangler::decodeNumber(const char *Mangled, unsigned long &Ret) {
|
||||
unsigned long Digit = Mangled[0] - '0';
|
||||
|
||||
// Check for overflow.
|
||||
if (Val > (std::numeric_limits<unsigned int>::max() - Digit) / 10)
|
||||
return nullptr;
|
||||
if (Val > (std::numeric_limits<unsigned int>::max() - Digit) / 10) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
Val = Val * 10 + Digit;
|
||||
++Mangled;
|
||||
} while (std::isdigit(*Mangled));
|
||||
Mangled.remove_prefix(1);
|
||||
} while (!Mangled.empty() && std::isdigit(Mangled.front()));
|
||||
|
||||
if (*Mangled == '\0')
|
||||
return nullptr;
|
||||
if (Mangled.empty()) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
Ret = Val;
|
||||
return Mangled;
|
||||
}
|
||||
|
||||
const char *Demangler::decodeBackrefPos(const char *Mangled, long &Ret) {
|
||||
bool Demangler::decodeBackrefPos(std::string_view &Mangled, long &Ret) {
|
||||
// Return nullptr if trying to extract something that isn't a digit
|
||||
if (Mangled == nullptr || !std::isalpha(*Mangled))
|
||||
return nullptr;
|
||||
|
||||
if (Mangled.empty()) {
|
||||
Mangled = {};
|
||||
return false;
|
||||
}
|
||||
// Any identifier or non-basic type that has been emitted to the mangled
|
||||
// symbol before will not be emitted again, but is referenced by a special
|
||||
// sequence encoding the relative position of the original occurrence in the
|
||||
@@ -221,7 +219,7 @@ const char *Demangler::decodeBackrefPos(const char *Mangled, long &Ret) {
|
||||
// ^
|
||||
unsigned long Val = 0;
|
||||
|
||||
while (std::isalpha(*Mangled)) {
|
||||
while (!Mangled.empty() && std::isalpha(Mangled.front())) {
|
||||
// Check for overflow
|
||||
if (Val > (std::numeric_limits<unsigned long>::max() - 25) / 26)
|
||||
break;
|
||||
@@ -233,116 +231,133 @@ const char *Demangler::decodeBackrefPos(const char *Mangled, long &Ret) {
|
||||
if ((long)Val <= 0)
|
||||
break;
|
||||
Ret = Val;
|
||||
return Mangled + 1;
|
||||
Mangled.remove_prefix(1);
|
||||
return true;
|
||||
}
|
||||
|
||||
Val += Mangled[0] - 'A';
|
||||
++Mangled;
|
||||
Mangled.remove_prefix(1);
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
Mangled = {};
|
||||
return false;
|
||||
}
|
||||
|
||||
const char *Demangler::decodeBackref(const char *Mangled, const char *&Ret) {
|
||||
assert(Mangled != nullptr && *Mangled == 'Q' && "Invalid back reference!");
|
||||
Ret = nullptr;
|
||||
bool Demangler::decodeBackref(std::string_view &Mangled,
|
||||
std::string_view &Ret) {
|
||||
assert(!Mangled.empty() && Mangled.front() == 'Q' &&
|
||||
"Invalid back reference!");
|
||||
Ret = {};
|
||||
|
||||
// Position of 'Q'
|
||||
const char *Qpos = Mangled;
|
||||
const char *Qpos = Mangled.data();
|
||||
long RefPos;
|
||||
++Mangled;
|
||||
Mangled.remove_prefix(1);
|
||||
|
||||
Mangled = decodeBackrefPos(Mangled, RefPos);
|
||||
if (Mangled == nullptr)
|
||||
return nullptr;
|
||||
if (!decodeBackrefPos(Mangled, RefPos)) {
|
||||
Mangled = {};
|
||||
return false;
|
||||
}
|
||||
|
||||
if (RefPos > Qpos - Str)
|
||||
return nullptr;
|
||||
if (RefPos > Qpos - Str.data()) {
|
||||
Mangled = {};
|
||||
return false;
|
||||
}
|
||||
|
||||
// Set the position of the back reference.
|
||||
Ret = Qpos - RefPos;
|
||||
|
||||
return Mangled;
|
||||
return true;
|
||||
}
|
||||
|
||||
const char *Demangler::parseSymbolBackref(OutputBuffer *Demangled,
|
||||
const char *Mangled) {
|
||||
void Demangler::parseSymbolBackref(OutputBuffer *Demangled,
|
||||
std::string_view &Mangled) {
|
||||
// An identifier back reference always points to a digit 0 to 9.
|
||||
// IdentifierBackRef:
|
||||
// Q NumberBackRef
|
||||
// ^
|
||||
const char *Backref;
|
||||
unsigned long Len;
|
||||
|
||||
// Get position of the back reference
|
||||
Mangled = decodeBackref(Mangled, Backref);
|
||||
std::string_view Backref;
|
||||
if (!decodeBackref(Mangled, Backref)) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
// Must point to a simple identifier
|
||||
Backref = decodeNumber(Backref, Len);
|
||||
if (Backref == nullptr || strlen(Backref) < Len)
|
||||
return nullptr;
|
||||
decodeNumber(Backref, Len);
|
||||
if (Backref.empty() || Backref.length() < Len) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
Backref = parseLName(Demangled, Backref, Len);
|
||||
if (Backref == nullptr)
|
||||
return nullptr;
|
||||
|
||||
return Mangled;
|
||||
parseLName(Demangled, Backref, Len);
|
||||
if (Backref.empty())
|
||||
Mangled = {};
|
||||
}
|
||||
|
||||
const char *Demangler::parseTypeBackref(const char *Mangled) {
|
||||
void Demangler::parseTypeBackref(std::string_view &Mangled) {
|
||||
// A type back reference always points to a letter.
|
||||
// TypeBackRef:
|
||||
// Q NumberBackRef
|
||||
// ^
|
||||
const char *Backref;
|
||||
|
||||
// If we appear to be moving backwards through the mangle string, then
|
||||
// bail as this may be a recursive back reference.
|
||||
if (Mangled - Str >= LastBackref)
|
||||
return nullptr;
|
||||
if (Mangled.data() - Str.data() >= LastBackref) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
int SaveRefPos = LastBackref;
|
||||
LastBackref = Mangled - Str;
|
||||
LastBackref = Mangled.data() - Str.data();
|
||||
|
||||
// Get position of the back reference.
|
||||
Mangled = decodeBackref(Mangled, Backref);
|
||||
std::string_view Backref;
|
||||
if (!decodeBackref(Mangled, Backref)) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
// Can't decode back reference.
|
||||
if (Backref == nullptr)
|
||||
return nullptr;
|
||||
if (Backref.empty()) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: Add support for function type back references.
|
||||
Backref = parseType(Backref);
|
||||
if (!parseType(Backref))
|
||||
Mangled = {};
|
||||
|
||||
LastBackref = SaveRefPos;
|
||||
|
||||
if (Backref == nullptr)
|
||||
return nullptr;
|
||||
|
||||
return Mangled;
|
||||
if (Backref.empty())
|
||||
Mangled = {};
|
||||
}
|
||||
|
||||
bool Demangler::isSymbolName(const char *Mangled) {
|
||||
bool Demangler::isSymbolName(std::string_view Mangled) {
|
||||
long Ret;
|
||||
const char *Qref = Mangled;
|
||||
const char *Qref = Mangled.data();
|
||||
|
||||
if (std::isdigit(*Mangled))
|
||||
if (std::isdigit(Mangled.front()))
|
||||
return true;
|
||||
|
||||
// TODO: Handle template instances.
|
||||
|
||||
if (*Mangled != 'Q')
|
||||
if (Mangled.front() != 'Q')
|
||||
return false;
|
||||
|
||||
Mangled = decodeBackrefPos(Mangled + 1, Ret);
|
||||
if (Mangled == nullptr || Ret > Qref - Str)
|
||||
Mangled.remove_prefix(1);
|
||||
bool Valid = decodeBackrefPos(Mangled, Ret);
|
||||
if (!Valid || Ret > Qref - Str.data())
|
||||
return false;
|
||||
|
||||
return std::isdigit(Qref[-Ret]);
|
||||
}
|
||||
|
||||
const char *Demangler::parseMangle(OutputBuffer *Demangled,
|
||||
const char *Mangled) {
|
||||
void Demangler::parseMangle(OutputBuffer *Demangled,
|
||||
std::string_view &Mangled) {
|
||||
// A D mangled symbol is comprised of both scope and type information.
|
||||
// MangleName:
|
||||
// _D QualifiedName Type
|
||||
@@ -352,24 +367,24 @@ const char *Demangler::parseMangle(OutputBuffer *Demangled,
|
||||
// above location.
|
||||
// Note that type is never a function type, but only the return type of
|
||||
// a function or the type of a variable.
|
||||
Mangled += 2;
|
||||
Mangled.remove_prefix(2);
|
||||
|
||||
Mangled = parseQualified(Demangled, Mangled);
|
||||
parseQualified(Demangled, Mangled);
|
||||
|
||||
if (Mangled != nullptr) {
|
||||
// Artificial symbols end with 'Z' and have no type.
|
||||
if (*Mangled == 'Z')
|
||||
++Mangled;
|
||||
else {
|
||||
Mangled = parseType(Mangled);
|
||||
}
|
||||
if (Mangled.empty()) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
return Mangled;
|
||||
// Artificial symbols end with 'Z' and have no type.
|
||||
if (Mangled.front() == 'Z') {
|
||||
Mangled.remove_prefix(1);
|
||||
} else if (!parseType(Mangled))
|
||||
Mangled = {};
|
||||
}
|
||||
|
||||
const char *Demangler::parseQualified(OutputBuffer *Demangled,
|
||||
const char *Mangled) {
|
||||
void Demangler::parseQualified(OutputBuffer *Demangled,
|
||||
std::string_view &Mangled) {
|
||||
// Qualified names are identifiers separated by their encoded length.
|
||||
// Nested functions also encode their argument types without specifying
|
||||
// what they return.
|
||||
@@ -388,10 +403,10 @@ const char *Demangler::parseQualified(OutputBuffer *Demangled,
|
||||
size_t NotFirst = false;
|
||||
do {
|
||||
// Skip over anonymous symbols.
|
||||
if (*Mangled == '0') {
|
||||
if (!Mangled.empty() && Mangled.front() == '0') {
|
||||
do
|
||||
++Mangled;
|
||||
while (*Mangled == '0');
|
||||
Mangled.remove_prefix(1);
|
||||
while (!Mangled.empty() && Mangled.front() == '0');
|
||||
|
||||
continue;
|
||||
}
|
||||
@@ -400,62 +415,63 @@ const char *Demangler::parseQualified(OutputBuffer *Demangled,
|
||||
*Demangled << '.';
|
||||
NotFirst = true;
|
||||
|
||||
Mangled = parseIdentifier(Demangled, Mangled);
|
||||
|
||||
} while (Mangled && isSymbolName(Mangled));
|
||||
|
||||
return Mangled;
|
||||
parseIdentifier(Demangled, Mangled);
|
||||
} while (!Mangled.empty() && isSymbolName(Mangled));
|
||||
}
|
||||
|
||||
const char *Demangler::parseIdentifier(OutputBuffer *Demangled,
|
||||
const char *Mangled) {
|
||||
unsigned long Len;
|
||||
void Demangler::parseIdentifier(OutputBuffer *Demangled,
|
||||
std::string_view &Mangled) {
|
||||
if (Mangled.empty()) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
if (Mangled == nullptr || *Mangled == '\0')
|
||||
return nullptr;
|
||||
|
||||
if (*Mangled == 'Q')
|
||||
if (Mangled.front() == 'Q')
|
||||
return parseSymbolBackref(Demangled, Mangled);
|
||||
|
||||
// TODO: Parse lengthless template instances.
|
||||
|
||||
const char *Endptr = decodeNumber(Mangled, Len);
|
||||
unsigned long Len;
|
||||
decodeNumber(Mangled, Len);
|
||||
|
||||
if (Endptr == nullptr || Len == 0)
|
||||
return nullptr;
|
||||
|
||||
if (strlen(Endptr) < Len)
|
||||
return nullptr;
|
||||
|
||||
Mangled = Endptr;
|
||||
if (Mangled.empty()) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
if (!Len || Mangled.length() < Len) {
|
||||
Mangled = {};
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: Parse template instances with a length prefix.
|
||||
|
||||
// There can be multiple different declarations in the same function that
|
||||
// have the same mangled name. To make the mangled names unique, a fake
|
||||
// parent in the form `__Sddd' is added to the symbol.
|
||||
if (Len >= 4 && Mangled[0] == '_' && Mangled[1] == '_' && Mangled[2] == 'S') {
|
||||
const char *NumPtr = Mangled + 3;
|
||||
while (NumPtr < (Mangled + Len) && std::isdigit(*NumPtr))
|
||||
++NumPtr;
|
||||
|
||||
if (Mangled + Len == NumPtr) {
|
||||
if (Len >= 4 && starts_with(Mangled, "__S")) {
|
||||
const size_t SuffixLen = Mangled.length() - Len;
|
||||
std::string_view P = Mangled.substr(3);
|
||||
while (P.length() > SuffixLen && std::isdigit(P.front()))
|
||||
P.remove_prefix(1);
|
||||
if (P.length() == SuffixLen) {
|
||||
// Skip over the fake parent.
|
||||
Mangled += Len;
|
||||
Mangled.remove_prefix(Len);
|
||||
return parseIdentifier(Demangled, Mangled);
|
||||
}
|
||||
|
||||
// Else demangle it as a plain identifier.
|
||||
}
|
||||
|
||||
return parseLName(Demangled, Mangled, Len);
|
||||
parseLName(Demangled, Mangled, Len);
|
||||
}
|
||||
|
||||
const char *Demangler::parseType(const char *Mangled) {
|
||||
if (*Mangled == '\0')
|
||||
return nullptr;
|
||||
bool Demangler::parseType(std::string_view &Mangled) {
|
||||
if (Mangled.empty()) {
|
||||
Mangled = {};
|
||||
return false;
|
||||
}
|
||||
|
||||
switch (*Mangled) {
|
||||
switch (Mangled.front()) {
|
||||
// TODO: Parse type qualifiers.
|
||||
// TODO: Parse function types.
|
||||
// TODO: Parse compound types.
|
||||
@@ -464,102 +480,102 @@ const char *Demangler::parseType(const char *Mangled) {
|
||||
|
||||
// Basic types.
|
||||
case 'i':
|
||||
++Mangled;
|
||||
Mangled.remove_prefix(1);
|
||||
// TODO: Add type name dumping
|
||||
return Mangled;
|
||||
return true;
|
||||
|
||||
// TODO: Add support for the rest of the basic types.
|
||||
|
||||
// Back referenced type.
|
||||
case 'Q':
|
||||
return parseTypeBackref(Mangled);
|
||||
case 'Q': {
|
||||
parseTypeBackref(Mangled);
|
||||
return true;
|
||||
}
|
||||
|
||||
default: // unhandled.
|
||||
return nullptr;
|
||||
Mangled = {};
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
const char *Demangler::parseLName(OutputBuffer *Demangled, const char *Mangled,
|
||||
unsigned long Len) {
|
||||
void Demangler::parseLName(OutputBuffer *Demangled, std::string_view &Mangled,
|
||||
unsigned long Len) {
|
||||
switch (Len) {
|
||||
case 6:
|
||||
if (strncmp(Mangled, "__initZ", Len + 1) == 0) {
|
||||
if (starts_with(Mangled, "__initZ")) {
|
||||
// The static initializer for a given symbol.
|
||||
Demangled->prepend("initializer for ");
|
||||
Demangled->setCurrentPosition(Demangled->getCurrentPosition() - 1);
|
||||
Mangled += Len;
|
||||
return Mangled;
|
||||
Mangled.remove_prefix(Len);
|
||||
return;
|
||||
}
|
||||
if (strncmp(Mangled, "__vtblZ", Len + 1) == 0) {
|
||||
if (starts_with(Mangled, "__vtblZ")) {
|
||||
// The vtable symbol for a given class.
|
||||
Demangled->prepend("vtable for ");
|
||||
Demangled->setCurrentPosition(Demangled->getCurrentPosition() - 1);
|
||||
Mangled += Len;
|
||||
return Mangled;
|
||||
Mangled.remove_prefix(Len);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
|
||||
case 7:
|
||||
if (strncmp(Mangled, "__ClassZ", Len + 1) == 0) {
|
||||
if (starts_with(Mangled, "__ClassZ")) {
|
||||
// The classinfo symbol for a given class.
|
||||
Demangled->prepend("ClassInfo for ");
|
||||
Demangled->setCurrentPosition(Demangled->getCurrentPosition() - 1);
|
||||
Mangled += Len;
|
||||
return Mangled;
|
||||
Mangled.remove_prefix(Len);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
|
||||
case 11:
|
||||
if (strncmp(Mangled, "__InterfaceZ", Len + 1) == 0) {
|
||||
if (starts_with(Mangled, "__InterfaceZ")) {
|
||||
// The interface symbol for a given class.
|
||||
Demangled->prepend("Interface for ");
|
||||
Demangled->setCurrentPosition(Demangled->getCurrentPosition() - 1);
|
||||
Mangled += Len;
|
||||
return Mangled;
|
||||
Mangled.remove_prefix(Len);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
|
||||
case 12:
|
||||
if (strncmp(Mangled, "__ModuleInfoZ", Len + 1) == 0) {
|
||||
if (starts_with(Mangled, "__ModuleInfoZ")) {
|
||||
// The ModuleInfo symbol for a given module.
|
||||
Demangled->prepend("ModuleInfo for ");
|
||||
Demangled->setCurrentPosition(Demangled->getCurrentPosition() - 1);
|
||||
Mangled += Len;
|
||||
return Mangled;
|
||||
Mangled.remove_prefix(Len);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
*Demangled << StringView(Mangled, Len);
|
||||
Mangled += Len;
|
||||
|
||||
return Mangled;
|
||||
*Demangled << Mangled.substr(0, Len);
|
||||
Mangled.remove_prefix(Len);
|
||||
}
|
||||
|
||||
Demangler::Demangler(const char *Mangled)
|
||||
: Str(Mangled), LastBackref(strlen(Mangled)) {}
|
||||
Demangler::Demangler(std::string_view Mangled)
|
||||
: Str(Mangled), LastBackref(Mangled.length()) {}
|
||||
|
||||
const char *Demangler::parseMangle(OutputBuffer *Demangled) {
|
||||
return parseMangle(Demangled, this->Str);
|
||||
std::string_view M(this->Str);
|
||||
parseMangle(Demangled, M);
|
||||
return M.data();
|
||||
}
|
||||
|
||||
char *llvm::dlangDemangle(const char *MangledName) {
|
||||
if (MangledName == nullptr || strncmp(MangledName, "_D", 2) != 0)
|
||||
char *llvm::dlangDemangle(std::string_view MangledName) {
|
||||
if (MangledName.empty() || !starts_with(MangledName, "_D"))
|
||||
return nullptr;
|
||||
|
||||
OutputBuffer Demangled;
|
||||
if (!initializeOutputBuffer(nullptr, nullptr, Demangled, 1024))
|
||||
return nullptr;
|
||||
|
||||
if (strcmp(MangledName, "_Dmain") == 0) {
|
||||
if (MangledName == "_Dmain") {
|
||||
Demangled << "D main";
|
||||
} else {
|
||||
|
||||
Demangler D = Demangler(MangledName);
|
||||
MangledName = D.parseMangle(&Demangled);
|
||||
Demangler D(MangledName);
|
||||
const char *M = D.parseMangle(&Demangled);
|
||||
|
||||
// Check that the entire symbol was successfully demangled.
|
||||
if (MangledName == nullptr || *MangledName != '\0') {
|
||||
if (M == nullptr || *M != '\0') {
|
||||
std::free(Demangled.getBuffer());
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
46
lib/external/llvm-demangle/source/Demangle.cpp
vendored
46
lib/external/llvm-demangle/source/Demangle.cpp
vendored
@@ -11,45 +11,45 @@
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/Demangle/Demangle.h"
|
||||
#include "llvm/Demangle/StringViewExtras.h"
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <string_view>
|
||||
|
||||
static bool isItaniumEncoding(const char *S) {
|
||||
// Itanium encoding requires 1 or 3 leading underscores, followed by 'Z'.
|
||||
return std::strncmp(S, "_Z", 2) == 0 || std::strncmp(S, "___Z", 4) == 0;
|
||||
}
|
||||
using llvm::itanium_demangle::starts_with;
|
||||
|
||||
static bool isRustEncoding(const char *S) { return S[0] == '_' && S[1] == 'R'; }
|
||||
|
||||
static bool isDLangEncoding(const std::string &MangledName) {
|
||||
return MangledName.size() >= 2 && MangledName[0] == '_' &&
|
||||
MangledName[1] == 'D';
|
||||
}
|
||||
|
||||
std::string llvm::demangle(const std::string &MangledName) {
|
||||
std::string llvm::demangle(std::string_view MangledName) {
|
||||
std::string Result;
|
||||
const char *S = MangledName.c_str();
|
||||
|
||||
if (nonMicrosoftDemangle(S, Result))
|
||||
if (nonMicrosoftDemangle(MangledName, Result))
|
||||
return Result;
|
||||
|
||||
if (S[0] == '_' && nonMicrosoftDemangle(S + 1, Result))
|
||||
if (starts_with(MangledName, '_') &&
|
||||
nonMicrosoftDemangle(MangledName.substr(1), Result))
|
||||
return Result;
|
||||
|
||||
if (char *Demangled =
|
||||
microsoftDemangle(S, nullptr, nullptr, nullptr, nullptr)) {
|
||||
if (char *Demangled = microsoftDemangle(MangledName, nullptr, nullptr)) {
|
||||
Result = Demangled;
|
||||
std::free(Demangled);
|
||||
return Result;
|
||||
} else {
|
||||
Result = MangledName;
|
||||
}
|
||||
|
||||
return MangledName;
|
||||
return Result;
|
||||
}
|
||||
|
||||
bool llvm::nonMicrosoftDemangle(const char *MangledName, std::string &Result) {
|
||||
static bool isItaniumEncoding(std::string_view S) {
|
||||
// Itanium encoding requires 1 or 3 leading underscores, followed by 'Z'.
|
||||
return starts_with(S, "_Z") || starts_with(S, "___Z");
|
||||
}
|
||||
|
||||
static bool isRustEncoding(std::string_view S) { return starts_with(S, "_R"); }
|
||||
|
||||
static bool isDLangEncoding(std::string_view S) { return starts_with(S, "_D"); }
|
||||
|
||||
bool llvm::nonMicrosoftDemangle(std::string_view MangledName,
|
||||
std::string &Result) {
|
||||
char *Demangled = nullptr;
|
||||
if (isItaniumEncoding(MangledName))
|
||||
Demangled = itaniumDemangle(MangledName, nullptr, nullptr, nullptr);
|
||||
Demangled = itaniumDemangle(MangledName);
|
||||
else if (isRustEncoding(MangledName))
|
||||
Demangled = rustDemangle(MangledName);
|
||||
else if (isDLangEncoding(MangledName))
|
||||
|
||||
@@ -18,6 +18,7 @@
|
||||
#include <cstdio>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <exception>
|
||||
#include <functional>
|
||||
#include <utility>
|
||||
|
||||
@@ -78,8 +79,8 @@ struct DumpVisitor {
|
||||
}
|
||||
|
||||
void printStr(const char *S) { fprintf(stderr, "%s", S); }
|
||||
void print(StringView SV) {
|
||||
fprintf(stderr, "\"%.*s\"", (int)SV.size(), SV.begin());
|
||||
void print(std::string_view SV) {
|
||||
fprintf(stderr, "\"%.*s\"", (int)SV.size(), SV.data());
|
||||
}
|
||||
void print(const Node *N) {
|
||||
if (N)
|
||||
@@ -365,36 +366,21 @@ public:
|
||||
|
||||
using Demangler = itanium_demangle::ManglingParser<DefaultAllocator>;
|
||||
|
||||
char *llvm::itaniumDemangle(const char *MangledName, char *Buf,
|
||||
size_t *N, int *Status) {
|
||||
if (MangledName == nullptr || (Buf != nullptr && N == nullptr)) {
|
||||
if (Status)
|
||||
*Status = demangle_invalid_args;
|
||||
char *llvm::itaniumDemangle(std::string_view MangledName) {
|
||||
if (MangledName.empty())
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
int InternalStatus = demangle_success;
|
||||
Demangler Parser(MangledName, MangledName + std::strlen(MangledName));
|
||||
OutputBuffer OB;
|
||||
|
||||
Demangler Parser(MangledName.data(),
|
||||
MangledName.data() + MangledName.length());
|
||||
Node *AST = Parser.parse();
|
||||
if (!AST)
|
||||
return nullptr;
|
||||
|
||||
if (AST == nullptr)
|
||||
InternalStatus = demangle_invalid_mangled_name;
|
||||
else if (!initializeOutputBuffer(Buf, N, OB, 1024))
|
||||
InternalStatus = demangle_memory_alloc_failure;
|
||||
else {
|
||||
assert(Parser.ForwardTemplateRefs.empty());
|
||||
AST->print(OB);
|
||||
OB += '\0';
|
||||
if (N != nullptr)
|
||||
*N = OB.getCurrentPosition();
|
||||
Buf = OB.getBuffer();
|
||||
}
|
||||
|
||||
if (Status)
|
||||
*Status = InternalStatus;
|
||||
return InternalStatus == demangle_success ? Buf : nullptr;
|
||||
OutputBuffer OB;
|
||||
assert(Parser.ForwardTemplateRefs.empty());
|
||||
AST->print(OB);
|
||||
OB += '\0';
|
||||
return OB.getBuffer();
|
||||
}
|
||||
|
||||
ItaniumPartialDemangler::ItaniumPartialDemangler()
|
||||
@@ -427,9 +413,7 @@ bool ItaniumPartialDemangler::partialDemangle(const char *MangledName) {
|
||||
}
|
||||
|
||||
static char *printNode(const Node *RootNode, char *Buf, size_t *N) {
|
||||
OutputBuffer OB;
|
||||
if (!initializeOutputBuffer(Buf, N, OB, 128))
|
||||
return nullptr;
|
||||
OutputBuffer OB(Buf, N);
|
||||
RootNode->print(OB);
|
||||
OB += '\0';
|
||||
if (N != nullptr)
|
||||
@@ -472,9 +456,7 @@ char *ItaniumPartialDemangler::getFunctionDeclContextName(char *Buf,
|
||||
return nullptr;
|
||||
const Node *Name = static_cast<const FunctionEncoding *>(RootNode)->getName();
|
||||
|
||||
OutputBuffer OB;
|
||||
if (!initializeOutputBuffer(Buf, N, OB, 128))
|
||||
return nullptr;
|
||||
OutputBuffer OB(Buf, N);
|
||||
|
||||
KeepGoingLocalFunction:
|
||||
while (true) {
|
||||
@@ -525,9 +507,7 @@ char *ItaniumPartialDemangler::getFunctionParameters(char *Buf,
|
||||
return nullptr;
|
||||
NodeArray Params = static_cast<FunctionEncoding *>(RootNode)->getParams();
|
||||
|
||||
OutputBuffer OB;
|
||||
if (!initializeOutputBuffer(Buf, N, OB, 128))
|
||||
return nullptr;
|
||||
OutputBuffer OB(Buf, N);
|
||||
|
||||
OB += '(';
|
||||
Params.printWithComma(OB);
|
||||
@@ -543,9 +523,7 @@ char *ItaniumPartialDemangler::getFunctionReturnType(
|
||||
if (!isFunction())
|
||||
return nullptr;
|
||||
|
||||
OutputBuffer OB;
|
||||
if (!initializeOutputBuffer(Buf, N, OB, 128))
|
||||
return nullptr;
|
||||
OutputBuffer OB(Buf, N);
|
||||
|
||||
if (const Node *Ret =
|
||||
static_cast<const FunctionEncoding *>(RootNode)->getReturnType())
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -119,9 +119,8 @@ static void outputCallingConvention(OutputBuffer &OB, CallingConv CC) {
|
||||
|
||||
std::string Node::toString(OutputFlags Flags) const {
|
||||
OutputBuffer OB;
|
||||
initializeOutputBuffer(nullptr, nullptr, OB, 1024);
|
||||
this->output(OB, Flags);
|
||||
StringView SV = OB;
|
||||
std::string_view SV = OB;
|
||||
std::string Owned(SV.begin(), SV.end());
|
||||
std::free(OB.getBuffer());
|
||||
return Owned;
|
||||
@@ -159,7 +158,7 @@ void NodeArrayNode::output(OutputBuffer &OB, OutputFlags Flags) const {
|
||||
}
|
||||
|
||||
void NodeArrayNode::output(OutputBuffer &OB, OutputFlags Flags,
|
||||
StringView Separator) const {
|
||||
std::string_view Separator) const {
|
||||
if (Count == 0)
|
||||
return;
|
||||
if (Nodes[0])
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/Demangle/Demangle.h"
|
||||
#include "llvm/Demangle/StringView.h"
|
||||
#include "llvm/Demangle/StringViewExtras.h"
|
||||
#include "llvm/Demangle/Utility.h"
|
||||
|
||||
#include <algorithm>
|
||||
@@ -20,17 +20,18 @@
|
||||
#include <cstdint>
|
||||
#include <cstring>
|
||||
#include <limits>
|
||||
#include <string_view>
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
using llvm::itanium_demangle::OutputBuffer;
|
||||
using llvm::itanium_demangle::ScopedOverride;
|
||||
using llvm::itanium_demangle::StringView;
|
||||
using llvm::itanium_demangle::starts_with;
|
||||
|
||||
namespace {
|
||||
|
||||
struct Identifier {
|
||||
StringView Name;
|
||||
std::string_view Name;
|
||||
bool Punycode;
|
||||
|
||||
bool empty() const { return Name.empty(); }
|
||||
@@ -77,7 +78,7 @@ class Demangler {
|
||||
size_t RecursionLevel;
|
||||
size_t BoundLifetimes;
|
||||
// Input string that is being demangled with "_R" prefix removed.
|
||||
StringView Input;
|
||||
std::string_view Input;
|
||||
// Position in the input string.
|
||||
size_t Position;
|
||||
// When true, print methods append the output to the stream.
|
||||
@@ -92,7 +93,7 @@ public:
|
||||
|
||||
Demangler(size_t MaxRecursionLevel = 500);
|
||||
|
||||
bool demangle(StringView MangledName);
|
||||
bool demangle(std::string_view MangledName);
|
||||
|
||||
private:
|
||||
bool demanglePath(IsInType Type,
|
||||
@@ -128,10 +129,10 @@ private:
|
||||
uint64_t parseOptionalBase62Number(char Tag);
|
||||
uint64_t parseBase62Number();
|
||||
uint64_t parseDecimalNumber();
|
||||
uint64_t parseHexNumber(StringView &HexDigits);
|
||||
uint64_t parseHexNumber(std::string_view &HexDigits);
|
||||
|
||||
void print(char C);
|
||||
void print(StringView S);
|
||||
void print(std::string_view S);
|
||||
void printDecimalNumber(uint64_t N);
|
||||
void printBasicType(BasicType);
|
||||
void printLifetime(uint64_t Index);
|
||||
@@ -147,20 +148,13 @@ private:
|
||||
|
||||
} // namespace
|
||||
|
||||
char *llvm::rustDemangle(const char *MangledName) {
|
||||
if (MangledName == nullptr)
|
||||
return nullptr;
|
||||
|
||||
char *llvm::rustDemangle(std::string_view MangledName) {
|
||||
// Return early if mangled name doesn't look like a Rust symbol.
|
||||
StringView Mangled(MangledName);
|
||||
if (!Mangled.startsWith("_R"))
|
||||
if (MangledName.empty() || !starts_with(MangledName, "_R"))
|
||||
return nullptr;
|
||||
|
||||
Demangler D;
|
||||
if (!initializeOutputBuffer(nullptr, nullptr, D.Output, 1024))
|
||||
return nullptr;
|
||||
|
||||
if (!D.demangle(Mangled)) {
|
||||
if (!D.demangle(MangledName)) {
|
||||
std::free(D.Output.getBuffer());
|
||||
return nullptr;
|
||||
}
|
||||
@@ -193,20 +187,20 @@ static inline bool isValid(const char C) {
|
||||
// responsibility of the caller to free the memory behind the output stream.
|
||||
//
|
||||
// <symbol-name> = "_R" <path> [<instantiating-crate>]
|
||||
bool Demangler::demangle(StringView Mangled) {
|
||||
bool Demangler::demangle(std::string_view Mangled) {
|
||||
Position = 0;
|
||||
Error = false;
|
||||
Print = true;
|
||||
RecursionLevel = 0;
|
||||
BoundLifetimes = 0;
|
||||
|
||||
if (!Mangled.consumeFront("_R")) {
|
||||
if (!starts_with(Mangled, "_R")) {
|
||||
Error = true;
|
||||
return false;
|
||||
}
|
||||
Mangled.remove_prefix(2);
|
||||
size_t Dot = Mangled.find('.');
|
||||
Input = Mangled.substr(0, Dot);
|
||||
StringView Suffix = Mangled.dropFront(Dot);
|
||||
Input = Dot == std::string_view::npos ? Mangled : Mangled.substr(0, Dot);
|
||||
|
||||
demanglePath(IsInType::No);
|
||||
|
||||
@@ -218,9 +212,9 @@ bool Demangler::demangle(StringView Mangled) {
|
||||
if (Position != Input.size())
|
||||
Error = true;
|
||||
|
||||
if (!Suffix.empty()) {
|
||||
if (Dot != std::string_view::npos) {
|
||||
print(" (");
|
||||
print(Suffix);
|
||||
print(Mangled.substr(Dot));
|
||||
print(")");
|
||||
}
|
||||
|
||||
@@ -778,7 +772,7 @@ void Demangler::demangleConstInt() {
|
||||
if (consumeIf('n'))
|
||||
print('-');
|
||||
|
||||
StringView HexDigits;
|
||||
std::string_view HexDigits;
|
||||
uint64_t Value = parseHexNumber(HexDigits);
|
||||
if (HexDigits.size() <= 16) {
|
||||
printDecimalNumber(Value);
|
||||
@@ -791,7 +785,7 @@ void Demangler::demangleConstInt() {
|
||||
// <const-data> = "0_" // false
|
||||
// | "1_" // true
|
||||
void Demangler::demangleConstBool() {
|
||||
StringView HexDigits;
|
||||
std::string_view HexDigits;
|
||||
parseHexNumber(HexDigits);
|
||||
if (HexDigits == "0")
|
||||
print("false");
|
||||
@@ -808,7 +802,7 @@ static bool isAsciiPrintable(uint64_t CodePoint) {
|
||||
|
||||
// <const-data> = <hex-number>
|
||||
void Demangler::demangleConstChar() {
|
||||
StringView HexDigits;
|
||||
std::string_view HexDigits;
|
||||
uint64_t CodePoint = parseHexNumber(HexDigits);
|
||||
if (Error || HexDigits.size() > 6) {
|
||||
Error = true;
|
||||
@@ -862,7 +856,7 @@ Identifier Demangler::parseIdentifier() {
|
||||
Error = true;
|
||||
return {};
|
||||
}
|
||||
StringView S = Input.substr(Position, Bytes);
|
||||
std::string_view S = Input.substr(Position, Bytes);
|
||||
Position += Bytes;
|
||||
|
||||
if (!std::all_of(S.begin(), S.end(), isValid)) {
|
||||
@@ -970,7 +964,7 @@ uint64_t Demangler::parseDecimalNumber() {
|
||||
//
|
||||
// <hex-number> = "0_"
|
||||
// | <1-9a-f> {<0-9a-f>} "_"
|
||||
uint64_t Demangler::parseHexNumber(StringView &HexDigits) {
|
||||
uint64_t Demangler::parseHexNumber(std::string_view &HexDigits) {
|
||||
size_t Start = Position;
|
||||
uint64_t Value = 0;
|
||||
|
||||
@@ -994,7 +988,7 @@ uint64_t Demangler::parseHexNumber(StringView &HexDigits) {
|
||||
}
|
||||
|
||||
if (Error) {
|
||||
HexDigits = StringView();
|
||||
HexDigits = std::string_view();
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1011,7 +1005,7 @@ void Demangler::print(char C) {
|
||||
Output += C;
|
||||
}
|
||||
|
||||
void Demangler::print(StringView S) {
|
||||
void Demangler::print(std::string_view S) {
|
||||
if (Error || !Print)
|
||||
return;
|
||||
|
||||
@@ -1108,17 +1102,17 @@ static inline bool encodeUTF8(size_t CodePoint, char *Output) {
|
||||
|
||||
// Decodes string encoded using punycode and appends results to Output.
|
||||
// Returns true if decoding was successful.
|
||||
static bool decodePunycode(StringView Input, OutputBuffer &Output) {
|
||||
static bool decodePunycode(std::string_view Input, OutputBuffer &Output) {
|
||||
size_t OutputSize = Output.getCurrentPosition();
|
||||
size_t InputIdx = 0;
|
||||
|
||||
// Rust uses an underscore as a delimiter.
|
||||
size_t DelimiterPos = StringView::npos;
|
||||
size_t DelimiterPos = std::string_view::npos;
|
||||
for (size_t I = 0; I != Input.size(); ++I)
|
||||
if (Input[I] == '_')
|
||||
DelimiterPos = I;
|
||||
|
||||
if (DelimiterPos != StringView::npos) {
|
||||
if (DelimiterPos != std::string_view::npos) {
|
||||
// Copy basic code points before the last delimiter to the output.
|
||||
for (; InputIdx != DelimiterPos; ++InputIdx) {
|
||||
char C = Input[InputIdx];
|
||||
@@ -1126,7 +1120,7 @@ static bool decodePunycode(StringView Input, OutputBuffer &Output) {
|
||||
return false;
|
||||
// Code points are padded with zeros while decoding is in progress.
|
||||
char UTF8[4] = {C};
|
||||
Output += StringView(UTF8, UTF8 + 4);
|
||||
Output += std::string_view(UTF8, 4);
|
||||
}
|
||||
// Skip over the delimiter.
|
||||
++InputIdx;
|
||||
|
||||
@@ -5,7 +5,6 @@
|
||||
#include <utility>
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
#include <set>
|
||||
#include <span>
|
||||
|
||||
#include <hex/api/event.hpp>
|
||||
@@ -148,7 +147,7 @@ namespace hex {
|
||||
if (this->m_icon.isValid())
|
||||
return m_icon;
|
||||
|
||||
this->m_icon = ImGui::Texture(reinterpret_cast<const u8*>(this->m_iconData.data()), this->m_iconData.size());
|
||||
this->m_icon = ImGui::Texture(this->m_iconData.data(), this->m_iconData.size());
|
||||
|
||||
return this->m_icon;
|
||||
}
|
||||
@@ -350,7 +349,7 @@ namespace hex {
|
||||
*/
|
||||
template<std::derived_from<Achievement> T = Achievement>
|
||||
static Achievement& addTemporaryAchievement(auto && ... args) {
|
||||
auto &achievement = addAchievement(std::forward<decltype(args)>(args)...);
|
||||
auto &achievement = addAchievement<T>(std::forward<decltype(args)>(args)...);
|
||||
|
||||
achievement.m_temporary = true;
|
||||
|
||||
|
||||
@@ -56,7 +56,7 @@ namespace hex {
|
||||
};
|
||||
|
||||
template<typename... Params>
|
||||
struct Event : public EventBase {
|
||||
struct Event : EventBase {
|
||||
using Callback = std::function<void(Params...)>;
|
||||
|
||||
explicit Event(Callback func) noexcept : m_func(std::move(func)) { }
|
||||
|
||||
@@ -2,14 +2,11 @@
|
||||
|
||||
#include <hex.hpp>
|
||||
|
||||
#include <list>
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <variant>
|
||||
#include <map>
|
||||
|
||||
#include <hex/helpers/concepts.hpp>
|
||||
#include <hex/api/keybinding.hpp>
|
||||
|
||||
#include <wolv/io/fs.hpp>
|
||||
@@ -58,7 +55,7 @@ namespace hex {
|
||||
color_t m_color = 0x00;
|
||||
};
|
||||
|
||||
struct ProviderRegion : public Region {
|
||||
struct ProviderRegion : Region {
|
||||
prv::Provider *provider;
|
||||
|
||||
[[nodiscard]] prv::Provider *getProvider() const { return this->provider; }
|
||||
@@ -320,6 +317,7 @@ namespace hex {
|
||||
* @brief Creates a new provider using its unlocalized name and add it to the list of providers
|
||||
* @param unlocalizedName The unlocalized name of the provider to create
|
||||
* @param skipLoadInterface Whether to skip the provider's loading interface (see property documentation)
|
||||
* @param select Whether to select the provider after adding it
|
||||
*/
|
||||
prv::Provider* createProvider(const std::string &unlocalizedName, bool skipLoadInterface = false, bool select = true);
|
||||
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
#include <GLFW/glfw3.h>
|
||||
|
||||
#include <functional>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <set>
|
||||
#include <string>
|
||||
@@ -161,7 +160,7 @@ namespace hex {
|
||||
Shortcut() = default;
|
||||
Shortcut(Keys key) : m_keys({ key }) { }
|
||||
|
||||
const static inline auto None = Keys(0);
|
||||
constexpr static inline auto None = Keys(0);
|
||||
|
||||
Shortcut operator+(const Key &other) const {
|
||||
Shortcut result = *this;
|
||||
|
||||
@@ -1,13 +1,10 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex.hpp>
|
||||
#include <hex/helpers/fs.hpp>
|
||||
|
||||
#include <string>
|
||||
#include <variant>
|
||||
|
||||
#include <nlohmann/json_fwd.hpp>
|
||||
#include <imgui.h>
|
||||
|
||||
namespace hex {
|
||||
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <initializer_list>
|
||||
#include <map>
|
||||
#include <string>
|
||||
#include <string_view>
|
||||
|
||||
@@ -1,8 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex.hpp>
|
||||
|
||||
#include <hex/helpers/fmt.hpp>
|
||||
#include <hex/helpers/fs.hpp>
|
||||
|
||||
#include <span>
|
||||
@@ -84,8 +81,7 @@ namespace hex {
|
||||
return reinterpret_cast<T>(this->getPluginFunction(symbol));
|
||||
}
|
||||
|
||||
private:
|
||||
[[nodiscard]] void *getPluginFunction(const std::string &symbol);
|
||||
[[nodiscard]] void *getPluginFunction(const std::string &symbol) const;
|
||||
};
|
||||
|
||||
class PluginManager {
|
||||
|
||||
@@ -1,15 +1,10 @@
|
||||
#pragma once
|
||||
|
||||
#include <list>
|
||||
#include <string>
|
||||
#include <string_view>
|
||||
|
||||
#include <hex/api/imhex_api.hpp>
|
||||
#include <hex/api/event.hpp>
|
||||
|
||||
#include <hex/helpers/fs.hpp>
|
||||
#include <hex/helpers/utils.hpp>
|
||||
#include <hex/helpers/concepts.hpp>
|
||||
#include <hex/helpers/tar.hpp>
|
||||
|
||||
/**
|
||||
|
||||
@@ -5,7 +5,6 @@
|
||||
#include <cstdio>
|
||||
#include <thread>
|
||||
#include <functional>
|
||||
#include <cstdint>
|
||||
#include <mutex>
|
||||
#include <chrono>
|
||||
#include <memory>
|
||||
@@ -112,7 +111,7 @@ namespace hex {
|
||||
|
||||
[[nodiscard]] u32 getProgress() const;
|
||||
|
||||
void interrupt();
|
||||
void interrupt() const;
|
||||
private:
|
||||
std::weak_ptr<Task> m_task;
|
||||
};
|
||||
|
||||
@@ -1,2 +1,4 @@
|
||||
constexpr static const auto ImHexApiURL = "https://api.werwolv.net/imhex";
|
||||
constexpr static const auto GitHubApiURL = "https://api.github.com/repos/WerWolv/ImHex";
|
||||
#pragma once
|
||||
|
||||
constexpr static auto ImHexApiURL = "https://api.werwolv.net/imhex";
|
||||
constexpr static auto GitHubApiURL = "https://api.github.com/repos/WerWolv/ImHex";
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
#pragma once
|
||||
#include <hex.hpp>
|
||||
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <string_view>
|
||||
#include <map>
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex.hpp>
|
||||
|
||||
namespace hex::dp {
|
||||
|
||||
class Link {
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex.hpp>
|
||||
|
||||
#include <hex/helpers/intrinsics.hpp>
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex.hpp>
|
||||
|
||||
#include <type_traits>
|
||||
#include <memory>
|
||||
|
||||
@@ -18,6 +16,7 @@ namespace hex {
|
||||
template<typename T>
|
||||
class ICloneable {
|
||||
public:
|
||||
virtual ~ICloneable() = default;
|
||||
[[nodiscard]] virtual std::unique_ptr<T> clone() const = 0;
|
||||
};
|
||||
|
||||
|
||||
@@ -3,7 +3,6 @@
|
||||
#include <hex.hpp>
|
||||
|
||||
#include <array>
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
@@ -16,9 +15,9 @@ namespace hex::crypt {
|
||||
void initialize();
|
||||
void exit();
|
||||
|
||||
u8 crc8(prv::Provider *&data, u64 offset, size_t size, u32 polynomial, u32 init, u32 xorout, bool reflectIn, bool reflectOut);
|
||||
u16 crc16(prv::Provider *&data, u64 offset, size_t size, u32 polynomial, u32 init, u32 xorout, bool reflectIn, bool reflectOut);
|
||||
u32 crc32(prv::Provider *&data, u64 offset, size_t size, u32 polynomial, u32 init, u32 xorout, bool reflectIn, bool reflectOut);
|
||||
u8 crc8(prv::Provider *&data, u64 offset, size_t size, u32 polynomial, u32 init, u32 xorOut, bool reflectIn, bool reflectOut);
|
||||
u16 crc16(prv::Provider *&data, u64 offset, size_t size, u32 polynomial, u32 init, u32 xorOut, bool reflectIn, bool reflectOut);
|
||||
u32 crc32(prv::Provider *&data, u64 offset, size_t size, u32 polynomial, u32 init, u32 xorOut, bool reflectIn, bool reflectOut);
|
||||
|
||||
std::array<u8, 16> md5(prv::Provider *&data, u64 offset, size_t size);
|
||||
std::array<u8, 20> sha1(prv::Provider *&data, u64 offset, size_t size);
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <wolv/types/static_string.hpp>
|
||||
#include <wolv/utils/preproc.hpp>
|
||||
|
||||
#include <hex/ui/imgui_imhex_extensions.h>
|
||||
|
||||
@@ -42,11 +42,11 @@ namespace hex {
|
||||
return static_cast<cs_arch>(architecture);
|
||||
}
|
||||
|
||||
static inline bool isSupported(Architecture architecture) {
|
||||
static bool isSupported(Architecture architecture) {
|
||||
return cs_support(toCapstoneArchitecture(architecture));
|
||||
}
|
||||
|
||||
constexpr static auto ArchitectureNames = [](){
|
||||
constexpr static auto ArchitectureNames = []{
|
||||
std::array<const char *, static_cast<u32>(Architecture::MAX) + 1> names = { };
|
||||
|
||||
names[CS_ARCH_ARM] = "ARM";
|
||||
@@ -74,7 +74,7 @@ namespace hex {
|
||||
return names;
|
||||
}();
|
||||
|
||||
static inline i32 getArchitectureSupportedCount() {
|
||||
static i32 getArchitectureSupportedCount() {
|
||||
static i32 supportedCount = -1;
|
||||
|
||||
if (supportedCount != -1) {
|
||||
|
||||
@@ -7,8 +7,6 @@
|
||||
#include <vector>
|
||||
#include <span>
|
||||
|
||||
#include <hex/helpers/fs.hpp>
|
||||
|
||||
#include <wolv/io/file.hpp>
|
||||
|
||||
namespace hex {
|
||||
@@ -22,12 +20,12 @@ namespace hex {
|
||||
|
||||
EncodingFile();
|
||||
EncodingFile(const EncodingFile &other);
|
||||
EncodingFile(EncodingFile &&other);
|
||||
EncodingFile(EncodingFile &&other) noexcept;
|
||||
EncodingFile(Type type, const std::fs::path &path);
|
||||
EncodingFile(Type type, const std::string &path);
|
||||
EncodingFile(Type type, const std::string &content);
|
||||
|
||||
EncodingFile& operator=(const EncodingFile &other);
|
||||
EncodingFile& operator=(EncodingFile &&other);
|
||||
EncodingFile& operator=(EncodingFile &&other) noexcept;
|
||||
|
||||
[[nodiscard]] std::pair<std::string_view, size_t> getEncodingFor(std::span<u8> buffer) const;
|
||||
[[nodiscard]] size_t getEncodingLengthFor(std::span<u8> buffer) const;
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
namespace hex {
|
||||
|
||||
template<typename... Args>
|
||||
inline std::string format(std::string_view format, Args... args) {
|
||||
std::string format(std::string_view format, Args... args) {
|
||||
return fmt::format(fmt::runtime(format), args...);
|
||||
}
|
||||
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
|
||||
#include <hex.hpp>
|
||||
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <filesystem>
|
||||
|
||||
@@ -7,16 +7,12 @@
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include <hex/helpers/logger.hpp>
|
||||
#include <hex/helpers/fmt.hpp>
|
||||
|
||||
#include <wolv/io/file.hpp>
|
||||
#include <wolv/utils/core.hpp>
|
||||
#include <wolv/utils/guards.hpp>
|
||||
#include <wolv/utils/string.hpp>
|
||||
|
||||
#include <mbedtls/ssl.h>
|
||||
|
||||
#if defined(OS_WEB)
|
||||
#include <emscripten/fetch.h>
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include<future>
|
||||
#include <future>
|
||||
|
||||
#include <emscripten/fetch.h>
|
||||
|
||||
|
||||
@@ -1,10 +1,12 @@
|
||||
#pragma once
|
||||
|
||||
#include<string>
|
||||
#include<future>
|
||||
#include <string>
|
||||
#include <future>
|
||||
|
||||
#include <curl/curl.h>
|
||||
|
||||
#include <hex/helpers/logger.hpp>
|
||||
|
||||
namespace hex {
|
||||
|
||||
template<typename T>
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
namespace hex {
|
||||
|
||||
inline void unused(auto && ... x) {
|
||||
void unused(auto && ... x) {
|
||||
((void)x, ...);
|
||||
}
|
||||
|
||||
|
||||
@@ -4,19 +4,19 @@ namespace hex::literals {
|
||||
|
||||
/* Byte literals */
|
||||
|
||||
constexpr static inline unsigned long long operator""_Bytes(unsigned long long bytes) noexcept {
|
||||
constexpr static unsigned long long operator""_Bytes(unsigned long long bytes) noexcept {
|
||||
return bytes;
|
||||
}
|
||||
|
||||
constexpr static inline unsigned long long operator""_KiB(unsigned long long kiB) noexcept {
|
||||
constexpr static unsigned long long operator""_KiB(unsigned long long kiB) noexcept {
|
||||
return operator""_Bytes(kiB * 1024);
|
||||
}
|
||||
|
||||
constexpr static inline unsigned long long operator""_MiB(unsigned long long MiB) noexcept {
|
||||
constexpr static unsigned long long operator""_MiB(unsigned long long MiB) noexcept {
|
||||
return operator""_KiB(MiB * 1024);
|
||||
}
|
||||
|
||||
constexpr static inline unsigned long long operator""_GiB(unsigned long long GiB) noexcept {
|
||||
constexpr static unsigned long long operator""_GiB(unsigned long long GiB) noexcept {
|
||||
return operator""_MiB(GiB * 1024);
|
||||
}
|
||||
|
||||
|
||||
@@ -30,12 +30,8 @@ namespace hex::log {
|
||||
};
|
||||
|
||||
std::vector<LogEntry>& getLogEntries();
|
||||
}
|
||||
|
||||
namespace {
|
||||
|
||||
|
||||
[[maybe_unused]] void printPrefix(FILE *dest, const fmt::text_style &ts, const std::string &level) {
|
||||
[[maybe_unused]] inline void printPrefix(FILE *dest, const fmt::text_style &ts, const std::string &level) {
|
||||
const auto now = fmt::localtime(std::chrono::system_clock::to_time_t(std::chrono::system_clock::now()));
|
||||
|
||||
fmt::print(dest, "[{0:%H:%M:%S}] ", now);
|
||||
@@ -68,26 +64,26 @@ namespace hex::log {
|
||||
|
||||
[[maybe_unused]] void debug(const std::string &fmt, auto && ... args) {
|
||||
#if defined(DEBUG)
|
||||
hex::log::print(fg(fmt::color::light_green) | fmt::emphasis::bold, "[DEBUG]", fmt, args...);
|
||||
hex::log::impl::print(fg(fmt::color::light_green) | fmt::emphasis::bold, "[DEBUG]", fmt, args...);
|
||||
#else
|
||||
impl::getLogEntries().push_back({ IMHEX_PROJECT_NAME, "[DEBUG]", fmt::format(fmt::runtime(fmt), args...) });
|
||||
#endif
|
||||
}
|
||||
|
||||
[[maybe_unused]] void info(const std::string &fmt, auto && ... args) {
|
||||
hex::log::print(fg(fmt::color::cadet_blue) | fmt::emphasis::bold, "[INFO] ", fmt, args...);
|
||||
hex::log::impl::print(fg(fmt::color::cadet_blue) | fmt::emphasis::bold, "[INFO] ", fmt, args...);
|
||||
}
|
||||
|
||||
[[maybe_unused]] void warn(const std::string &fmt, auto && ... args) {
|
||||
hex::log::print(fg(fmt::color::orange) | fmt::emphasis::bold, "[WARN] ", fmt, args...);
|
||||
hex::log::impl::print(fg(fmt::color::orange) | fmt::emphasis::bold, "[WARN] ", fmt, args...);
|
||||
}
|
||||
|
||||
[[maybe_unused]] void error(const std::string &fmt, auto && ... args) {
|
||||
hex::log::print(fg(fmt::color::red) | fmt::emphasis::bold, "[ERROR]", fmt, args...);
|
||||
hex::log::impl::print(fg(fmt::color::red) | fmt::emphasis::bold, "[ERROR]", fmt, args...);
|
||||
}
|
||||
|
||||
[[maybe_unused]] void fatal(const std::string &fmt, auto && ... args) {
|
||||
hex::log::print(fg(fmt::color::purple) | fmt::emphasis::bold, "[FATAL]", fmt, args...);
|
||||
hex::log::impl::print(fg(fmt::color::purple) | fmt::emphasis::bold, "[FATAL]", fmt, args...);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -20,7 +20,7 @@
|
||||
|
||||
namespace hex::gl {
|
||||
|
||||
namespace {
|
||||
namespace impl {
|
||||
|
||||
template<typename T>
|
||||
GLuint getType() {
|
||||
@@ -28,8 +28,10 @@ namespace hex::gl {
|
||||
return GL_FLOAT;
|
||||
else if constexpr (std::is_same_v<T, u32>)
|
||||
return GL_UNSIGNED_INT;
|
||||
else
|
||||
else {
|
||||
static_assert(hex::always_false<T>::value, "Unsupported type");
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -48,30 +50,30 @@ namespace hex::gl {
|
||||
|
||||
[[nodiscard]] size_t size() const { return this->m_data.size(); }
|
||||
|
||||
auto operator+(const Vector<T, Size>& other) {
|
||||
auto operator+(const Vector& other) {
|
||||
auto copy = *this;
|
||||
for (size_t i = 0; i < Size; i++)
|
||||
copy[i] += other[i];
|
||||
return copy;
|
||||
}
|
||||
|
||||
auto operator-(const Vector<T, Size>& other) {
|
||||
auto operator-(const Vector& other) {
|
||||
auto copy = *this;
|
||||
for (size_t i = 0; i < Size; i++)
|
||||
copy[i] -= other[i];
|
||||
return copy;
|
||||
}
|
||||
|
||||
auto dot(const Vector<T, Size>& other) {
|
||||
auto dot(const Vector& other) {
|
||||
T result = 0;
|
||||
for (size_t i = 0; i < Size; i++)
|
||||
result += this->m_data[i] * other[i];
|
||||
return result;
|
||||
}
|
||||
|
||||
auto cross(const Vector<T, Size>& other) {
|
||||
auto cross(const Vector& other) {
|
||||
static_assert(Size == 3, "Cross product is only defined for 3D vectors");
|
||||
return Vector<T, Size>({ this->m_data[1] * other[2] - this->m_data[2] * other[1], this->m_data[2] * other[0] - this->m_data[0] * other[2], this->m_data[0] * other[1] - this->m_data[1] * other[0] });
|
||||
return Vector({ this->m_data[1] * other[2] - this->m_data[2] * other[1], this->m_data[2] * other[0] - this->m_data[0] * other[2], this->m_data[0] * other[1] - this->m_data[1] * other[0] });
|
||||
}
|
||||
|
||||
auto normalize() {
|
||||
@@ -82,7 +84,7 @@ namespace hex::gl {
|
||||
return copy;
|
||||
}
|
||||
|
||||
auto operator==(const Vector<T, Size>& other) {
|
||||
auto operator==(const Vector& other) {
|
||||
for (size_t i = 0; i < Size; i++)
|
||||
if (this->m_data[i] != other[i])
|
||||
return false;
|
||||
@@ -167,7 +169,7 @@ namespace hex::gl {
|
||||
void addBuffer(u32 index, const Buffer<T> &buffer) const {
|
||||
glEnableVertexAttribArray(index);
|
||||
buffer.bind();
|
||||
glVertexAttribPointer(index, 3, getType<T>(), GL_FALSE, 3 * sizeof(T), nullptr);
|
||||
glVertexAttribPointer(index, 3, impl::getType<T>(), GL_FALSE, 3 * sizeof(T), nullptr);
|
||||
buffer.unbind();
|
||||
}
|
||||
|
||||
@@ -175,7 +177,7 @@ namespace hex::gl {
|
||||
void unbind() const;
|
||||
|
||||
private:
|
||||
GLuint m_array;
|
||||
GLuint m_array = 0;
|
||||
};
|
||||
|
||||
class Texture {
|
||||
|
||||
@@ -30,7 +30,7 @@ namespace hex {
|
||||
* @brief get the error string explaining the error that occured when opening the file.
|
||||
* This error is a combination of the tar error and the native file open error
|
||||
*/
|
||||
std::string getOpenErrorString();
|
||||
std::string getOpenErrorString() const;
|
||||
|
||||
[[nodiscard]] std::vector<u8> readVector(const std::fs::path &path);
|
||||
[[nodiscard]] std::string readString(const std::fs::path &path);
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
|
||||
#include <hex/helpers/concepts.hpp>
|
||||
#include <hex/helpers/fs.hpp>
|
||||
#include <hex/helpers/intrinsics.hpp>
|
||||
|
||||
#include <array>
|
||||
#include <bit>
|
||||
@@ -66,7 +65,7 @@ namespace hex {
|
||||
[[nodiscard]] std::string encodeByteString(const std::vector<u8> &bytes);
|
||||
[[nodiscard]] std::vector<u8> decodeByteString(const std::string &string);
|
||||
|
||||
[[nodiscard]] constexpr inline u64 extract(u8 from, u8 to, const std::unsigned_integral auto &value) {
|
||||
[[nodiscard]] constexpr u64 extract(u8 from, u8 to, const std::unsigned_integral auto &value) {
|
||||
if (from < to) std::swap(from, to);
|
||||
|
||||
using ValueType = std::remove_cvref_t<decltype(value)>;
|
||||
@@ -90,13 +89,13 @@ namespace hex {
|
||||
return (value & mask) >> to;
|
||||
}
|
||||
|
||||
[[nodiscard]] constexpr inline i128 signExtend(size_t numBits, i128 value) {
|
||||
[[nodiscard]] constexpr i128 signExtend(size_t numBits, i128 value) {
|
||||
i128 mask = 1ULL << (numBits - 1);
|
||||
return (value ^ mask) - mask;
|
||||
}
|
||||
|
||||
template<std::integral T>
|
||||
[[nodiscard]] constexpr inline T swapBitOrder(size_t numBits, T value) {
|
||||
[[nodiscard]] constexpr T swapBitOrder(size_t numBits, T value) {
|
||||
T result = 0x00;
|
||||
|
||||
for (size_t bit = 0; bit < numBits; bit++) {
|
||||
@@ -107,14 +106,14 @@ namespace hex {
|
||||
return result;
|
||||
}
|
||||
|
||||
[[nodiscard]] constexpr inline size_t strnlen(const char *s, size_t n) {
|
||||
[[nodiscard]] constexpr size_t strnlen(const char *s, size_t n) {
|
||||
size_t i = 0;
|
||||
while (i < n && s[i] != '\x00') i++;
|
||||
|
||||
return i;
|
||||
}
|
||||
|
||||
template<size_t Size>
|
||||
template<size_t>
|
||||
struct SizeTypeImpl { };
|
||||
|
||||
template<>
|
||||
@@ -215,7 +214,7 @@ namespace hex {
|
||||
|
||||
[[nodiscard]] inline std::vector<u8> parseByteString(const std::string &string) {
|
||||
auto byteString = std::string(string);
|
||||
byteString.erase(std::remove(byteString.begin(), byteString.end(), ' '), byteString.end());
|
||||
std::erase(byteString, ' ');
|
||||
|
||||
if ((byteString.length() % 2) != 0) return {};
|
||||
|
||||
@@ -230,11 +229,11 @@ namespace hex {
|
||||
return result;
|
||||
}
|
||||
|
||||
[[nodiscard]] inline std::string toBinaryString(std::unsigned_integral auto number) {
|
||||
[[nodiscard]] std::string toBinaryString(std::unsigned_integral auto number) {
|
||||
if (number == 0) return "0";
|
||||
|
||||
std::string result;
|
||||
for (i16 bit = hex::bit_width(number) - 1; bit >= 0; bit--)
|
||||
for (i16 bit = hex::bit_width(number) - 1; bit >= 0; bit -= 1)
|
||||
result += (number & (0b1 << bit)) == 0 ? '0' : '1';
|
||||
|
||||
return result;
|
||||
|
||||
@@ -1,8 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <span>
|
||||
#include <vector>
|
||||
|
||||
#include <hex/providers/provider.hpp>
|
||||
#include <hex/helpers/literals.hpp>
|
||||
|
||||
@@ -20,7 +17,7 @@ namespace hex::prv {
|
||||
public:
|
||||
using BufferedReader::BufferedReader;
|
||||
|
||||
ProviderReader(Provider *provider, size_t bufferSize = 0x100000) : BufferedReader(provider, provider->getActualSize(), bufferSize) {
|
||||
explicit ProviderReader(Provider *provider, size_t bufferSize = 0x100000) : BufferedReader(provider, provider->getActualSize(), bufferSize) {
|
||||
this->setEndAddress(provider->getBaseAddress() + provider->getActualSize() - 1);
|
||||
this->seek(provider->getBaseAddress());
|
||||
}
|
||||
|
||||
@@ -164,7 +164,7 @@ namespace hex::prv {
|
||||
virtual void saveAs(const std::fs::path &path);
|
||||
|
||||
|
||||
void applyOverlays(u64 offset, void *buffer, size_t size);
|
||||
void applyOverlays(u64 offset, void *buffer, size_t size) const;
|
||||
|
||||
[[nodiscard]] std::map<u64, u8> &getPatches();
|
||||
[[nodiscard]] const std::map<u64, u8> &getPatches() const;
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
#include <hex/api/event.hpp>
|
||||
#include <hex/providers/provider.hpp>
|
||||
|
||||
#include <concepts>
|
||||
#include <map>
|
||||
#include <utility>
|
||||
|
||||
|
||||
@@ -1,10 +1,11 @@
|
||||
#pragma once
|
||||
|
||||
#include<vector>
|
||||
#include<string>
|
||||
#include<functional>
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <functional>
|
||||
|
||||
namespace hex::subcommands {
|
||||
|
||||
/**
|
||||
* @brief Internal method - takes all the arguments ImHex received from the command line,
|
||||
* and determine which subcommands to run, with which arguments.
|
||||
@@ -27,4 +28,5 @@ namespace hex::subcommands {
|
||||
* @brief Register the handler for this specific command name
|
||||
*/
|
||||
void registerSubCommand(const std::string &cmdName, const ForwardCommandHandler &handler);
|
||||
|
||||
}
|
||||
|
||||
@@ -26,7 +26,7 @@ namespace hex {
|
||||
|
||||
class View {
|
||||
public:
|
||||
explicit View(std::string unlocalizedViewName);
|
||||
explicit View(std::string unlocalizedName);
|
||||
virtual ~View() = default;
|
||||
|
||||
virtual void drawContent() = 0;
|
||||
|
||||
@@ -7,7 +7,6 @@
|
||||
#include <hex/helpers/fmt.hpp>
|
||||
#include <hex/helpers/utils.hpp>
|
||||
|
||||
#include <wolv/io/file.hpp>
|
||||
#include <wolv/utils/string.hpp>
|
||||
|
||||
#include <utility>
|
||||
@@ -72,7 +71,7 @@ namespace hex {
|
||||
|
||||
static std::optional<ProviderRegion> s_currentSelection;
|
||||
void setCurrentSelection(std::optional<ProviderRegion> region) {
|
||||
s_currentSelection = region;
|
||||
s_currentSelection = std::move(region);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
|
||||
#include <hex/helpers/logger.hpp>
|
||||
#include <hex/helpers/utils.hpp>
|
||||
#include <hex/helpers/fmt.hpp>
|
||||
|
||||
#include <wolv/utils/string.hpp>
|
||||
|
||||
@@ -41,7 +42,7 @@ namespace hex {
|
||||
|
||||
Plugin::Plugin(hex::PluginFunctions functions) {
|
||||
this->m_handle = nullptr;
|
||||
this->m_functions = functions;
|
||||
this->m_functions = std::move(functions);
|
||||
}
|
||||
|
||||
|
||||
@@ -146,13 +147,13 @@ namespace hex {
|
||||
std::span<SubCommand> Plugin::getSubCommands() const {
|
||||
if (this->m_functions.getSubCommandsFunction != nullptr) {
|
||||
auto result = this->m_functions.getSubCommandsFunction();
|
||||
return *reinterpret_cast<std::vector<SubCommand>*>(result);
|
||||
return *static_cast<std::vector<SubCommand>*>(result);
|
||||
} else
|
||||
return { };
|
||||
}
|
||||
|
||||
|
||||
void *Plugin::getPluginFunction(const std::string &symbol) {
|
||||
void *Plugin::getPluginFunction(const std::string &symbol) const {
|
||||
#if defined(OS_WINDOWS)
|
||||
return reinterpret_cast<void *>(GetProcAddress(this->m_handle, symbol.c_str()));
|
||||
#else
|
||||
|
||||
@@ -1,12 +1,7 @@
|
||||
#include <hex/api/project_file_manager.hpp>
|
||||
|
||||
#include <hex/helpers/tar.hpp>
|
||||
#include <hex/helpers/fmt.hpp>
|
||||
#include <hex/helpers/logger.hpp>
|
||||
|
||||
#include <hex/providers/provider.hpp>
|
||||
|
||||
#include <wolv/utils/guards.hpp>
|
||||
#include <wolv/io/fs.hpp>
|
||||
|
||||
namespace hex {
|
||||
@@ -37,7 +32,7 @@ namespace hex {
|
||||
}
|
||||
|
||||
bool ProjectFile::store(std::optional<std::fs::path> filePath, bool updateLocation) {
|
||||
return s_storeProjectFunction(filePath, updateLocation);
|
||||
return s_storeProjectFunction(std::move(filePath), updateLocation);
|
||||
}
|
||||
|
||||
bool ProjectFile::hasPath() {
|
||||
|
||||
@@ -45,8 +45,8 @@ namespace hex {
|
||||
info.dwThreadID = ::GetCurrentThreadId();
|
||||
info.dwFlags = 0;
|
||||
|
||||
const DWORD MS_VC_EXCEPTION = 0x406D1388;
|
||||
RaiseException(MS_VC_EXCEPTION, 0, sizeof(info) / sizeof(ULONG_PTR), (ULONG_PTR*)&info);
|
||||
constexpr static DWORD MS_VC_EXCEPTION = 0x406D1388;
|
||||
RaiseException(MS_VC_EXCEPTION, 0, sizeof(info) / sizeof(ULONG_PTR), reinterpret_cast<ULONG_PTR*>(&info));
|
||||
#elif defined(OS_LINUX)
|
||||
pthread_setname_np(pthread_self(), name.c_str());
|
||||
#elif defined(OS_WEB)
|
||||
@@ -57,7 +57,7 @@ namespace hex {
|
||||
}
|
||||
|
||||
Task::Task(std::string unlocalizedName, u64 maxValue, bool background, std::function<void(Task &)> function)
|
||||
: m_unlocalizedName(std::move(unlocalizedName)), m_currValue(0), m_maxValue(maxValue), m_function(std::move(function)), m_background(background) { }
|
||||
: m_unlocalizedName(std::move(unlocalizedName)), m_maxValue(maxValue), m_function(std::move(function)), m_background(background) { }
|
||||
|
||||
Task::Task(hex::Task &&other) noexcept {
|
||||
{
|
||||
@@ -195,7 +195,7 @@ namespace hex {
|
||||
return !task->wasInterrupted();
|
||||
}
|
||||
|
||||
void TaskHolder::interrupt() {
|
||||
void TaskHolder::interrupt() const {
|
||||
if (this->m_task.expired())
|
||||
return;
|
||||
|
||||
@@ -208,7 +208,7 @@ namespace hex {
|
||||
return 0;
|
||||
|
||||
auto task = this->m_task.lock();
|
||||
return (u32)((task->getValue() * 100) / task->getMaxValue());
|
||||
return u32((task->getValue() * 100) / task->getMaxValue());
|
||||
}
|
||||
|
||||
|
||||
@@ -251,6 +251,7 @@ namespace hex {
|
||||
try {
|
||||
setThreadName(LangEntry(task->m_unlocalizedName));
|
||||
task->m_function(*task);
|
||||
setThreadName("Idle Task");
|
||||
log::debug("Finished task {}", task->m_unlocalizedName);
|
||||
} catch (const Task::TaskInterruptor &) {
|
||||
task->interruption();
|
||||
|
||||
@@ -89,7 +89,7 @@ namespace hex::crypt {
|
||||
constexpr Crc(u64 polynomial, u64 init, u64 xorOut, bool reflectInput, bool reflectOutput)
|
||||
: m_value(0x00), m_init(init & ((0b10ull << (NumBits - 1)) - 1)), m_xorOut(xorOut & ((0b10ull << (NumBits - 1)) - 1)),
|
||||
m_reflectInput(reflectInput), m_reflectOutput(reflectOutput),
|
||||
m_table([polynomial]() {
|
||||
m_table([polynomial] {
|
||||
auto reflectedPoly = reflect(polynomial & ((0b10ull << (NumBits - 1)) - 1), NumBits);
|
||||
std::array<uint64_t, 256> table = { 0 };
|
||||
|
||||
@@ -107,7 +107,7 @@ namespace hex::crypt {
|
||||
return table;
|
||||
}()) {
|
||||
reset();
|
||||
};
|
||||
}
|
||||
|
||||
constexpr void reset() {
|
||||
this->m_value = reflect(m_init, NumBits);
|
||||
@@ -363,9 +363,9 @@ namespace hex::crypt {
|
||||
std::vector<u8> decode64(const std::vector<u8> &input) {
|
||||
|
||||
size_t written = 0;
|
||||
mbedtls_base64_decode(nullptr, 0, &written, reinterpret_cast<const unsigned char *>(input.data()), input.size());
|
||||
mbedtls_base64_decode(nullptr, 0, &written, input.data(), input.size());
|
||||
std::vector<u8> output(written, 0x00);
|
||||
if (mbedtls_base64_decode(output.data(), output.size(), &written, reinterpret_cast<const unsigned char *>(input.data()), input.size()))
|
||||
if (mbedtls_base64_decode(output.data(), output.size(), &written, input.data(), input.size()))
|
||||
return {};
|
||||
|
||||
output.resize(written);
|
||||
@@ -376,10 +376,10 @@ namespace hex::crypt {
|
||||
std::vector<u8> encode64(const std::vector<u8> &input) {
|
||||
|
||||
size_t written = 0;
|
||||
mbedtls_base64_encode(nullptr, 0, &written, reinterpret_cast<const unsigned char *>(input.data()), input.size());
|
||||
mbedtls_base64_encode(nullptr, 0, &written, input.data(), input.size());
|
||||
|
||||
std::vector<u8> output(written, 0x00);
|
||||
if (mbedtls_base64_encode(output.data(), output.size(), &written, reinterpret_cast<const unsigned char *>(input.data()), input.size()))
|
||||
if (mbedtls_base64_encode(output.data(), output.size(), &written, input.data(), input.size()))
|
||||
return {};
|
||||
|
||||
output.resize(written);
|
||||
@@ -447,7 +447,7 @@ namespace hex::crypt {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if constexpr(std::is_signed<T>::value) {
|
||||
if constexpr(std::signed_integral<T>) {
|
||||
if ((b & 0x40) != 0) {
|
||||
value |= safeLeftShift(~static_cast<T>(0), shift);
|
||||
}
|
||||
@@ -470,7 +470,7 @@ namespace hex::crypt {
|
||||
while (true) {
|
||||
byte = value & 0x7F;
|
||||
value >>= 7;
|
||||
if constexpr(std::is_signed<T>::value) {
|
||||
if constexpr(std::signed_integral<T>) {
|
||||
if (value == 0 && (byte & 0x40) == 0) {
|
||||
break;
|
||||
}
|
||||
@@ -509,7 +509,7 @@ namespace hex::crypt {
|
||||
|
||||
|
||||
mbedtls_cipher_setup(&ctx, cipherInfo);
|
||||
mbedtls_cipher_setkey(&ctx, key.data(), static_cast<int>(key.size() * 8), operation);
|
||||
mbedtls_cipher_setkey(&ctx, key.data(), key.size() * 8, operation);
|
||||
|
||||
std::array<u8, 16> nonceCounter = { 0 };
|
||||
std::copy(nonce.begin(), nonce.end(), nonceCounter.begin());
|
||||
|
||||
@@ -19,7 +19,7 @@ namespace hex {
|
||||
this->m_name = other.m_name;
|
||||
}
|
||||
|
||||
EncodingFile::EncodingFile(EncodingFile &&other) {
|
||||
EncodingFile::EncodingFile(EncodingFile &&other) noexcept {
|
||||
this->m_mapping = std::move(other.m_mapping);
|
||||
this->m_tableContent = std::move(other.m_tableContent);
|
||||
this->m_longestSequence = other.m_longestSequence;
|
||||
@@ -72,7 +72,7 @@ namespace hex {
|
||||
return *this;
|
||||
}
|
||||
|
||||
EncodingFile &EncodingFile::operator=(EncodingFile &&other) {
|
||||
EncodingFile &EncodingFile::operator=(EncodingFile &&other) noexcept {
|
||||
this->m_mapping = std::move(other.m_mapping);
|
||||
this->m_tableContent = std::move(other.m_tableContent);
|
||||
this->m_longestSequence = other.m_longestSequence;
|
||||
@@ -90,7 +90,7 @@ namespace hex {
|
||||
|
||||
if (size > buffer.size()) continue;
|
||||
|
||||
std::vector<u8> key(buffer.begin(), buffer.begin() + size);
|
||||
std::vector key(buffer.begin(), buffer.begin() + size);
|
||||
if (mapping.contains(key))
|
||||
return { mapping.at(key), size };
|
||||
}
|
||||
@@ -104,7 +104,7 @@ namespace hex {
|
||||
|
||||
if (size > buffer.size()) continue;
|
||||
|
||||
std::vector<u8> key(buffer.begin(), buffer.begin() + size);
|
||||
std::vector key(buffer.begin(), buffer.begin() + size);
|
||||
if (mapping.contains(key))
|
||||
return size;
|
||||
}
|
||||
|
||||
@@ -24,7 +24,6 @@
|
||||
|
||||
#include <algorithm>
|
||||
#include <filesystem>
|
||||
#include <utility>
|
||||
|
||||
#include <wolv/io/file.hpp>
|
||||
#include <wolv/io/fs.hpp>
|
||||
@@ -245,7 +244,7 @@ namespace hex::fs {
|
||||
// Handle the path if the dialog was opened in single mode
|
||||
if (outPath != nullptr) {
|
||||
// Call the provided callback with the path
|
||||
callback(reinterpret_cast<char8_t*>(outPath.get()));
|
||||
callback(outPath.get());
|
||||
}
|
||||
|
||||
// Handle multiple paths if the dialog was opened in multiple mode
|
||||
@@ -256,7 +255,7 @@ namespace hex::fs {
|
||||
for (size_t i = 0; i < numPaths; i++) {
|
||||
NFD::UniquePathSetPath path;
|
||||
if (NFD::PathSet::GetPath(outPaths, i, path) == NFD_OKAY)
|
||||
callback(reinterpret_cast<char8_t*>(path.get()));
|
||||
callback(path.get());
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -425,9 +424,9 @@ namespace hex::fs {
|
||||
|
||||
// Remove all paths that don't exist if requested
|
||||
if (!listNonExisting) {
|
||||
result.erase(std::remove_if(result.begin(), result.end(), [](const auto &path) {
|
||||
return !wolv::io::fs::isDirectory(path);
|
||||
}), result.end());
|
||||
std::erase_if(result, [](const auto &entryPath) {
|
||||
return !wolv::io::fs::isDirectory(entryPath);
|
||||
});
|
||||
}
|
||||
|
||||
return result;
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
namespace hex {
|
||||
|
||||
size_t HttpRequest::writeToVector(void *contents, size_t size, size_t nmemb, void *userdata) {
|
||||
auto &response = *reinterpret_cast<std::vector<u8>*>(userdata);
|
||||
auto &response = *static_cast<std::vector<u8>*>(userdata);
|
||||
auto startSize = response.size();
|
||||
|
||||
response.resize(startSize + size * nmemb);
|
||||
@@ -15,9 +15,9 @@ namespace hex {
|
||||
}
|
||||
|
||||
size_t HttpRequest::writeToFile(void *contents, size_t size, size_t nmemb, void *userdata) {
|
||||
auto &file = *reinterpret_cast<wolv::io::File*>(userdata);
|
||||
auto &file = *static_cast<wolv::io::File*>(userdata);
|
||||
|
||||
file.writeBuffer(reinterpret_cast<const u8*>(contents), size * nmemb);
|
||||
file.writeBuffer(static_cast<const u8*>(contents), size * nmemb);
|
||||
|
||||
return size * nmemb;
|
||||
}
|
||||
|
||||
@@ -59,9 +59,9 @@ namespace hex::log::impl {
|
||||
return logEntries;
|
||||
}
|
||||
|
||||
void assertionHandler(bool expr, const char* expr_str, const char* file, int line) {
|
||||
void assertionHandler(bool expr, const char* exprString, const char* file, int line) {
|
||||
if (!expr) {
|
||||
log::error("Assertion failed: {} at {}:{}", expr_str, file, line);
|
||||
log::error("Assertion failed: {} at {}:{}", exprString, file, line);
|
||||
|
||||
#if defined (DEBUG)
|
||||
std::abort();
|
||||
|
||||
@@ -116,7 +116,7 @@ namespace hex::gl {
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
Buffer<T>::Buffer(Buffer<T> &&other) noexcept {
|
||||
Buffer<T>::Buffer(Buffer &&other) noexcept {
|
||||
this->m_buffer = other.m_buffer;
|
||||
this->m_size = other.m_size;
|
||||
this->m_type = other.m_type;
|
||||
@@ -124,7 +124,7 @@ namespace hex::gl {
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
Buffer<T>& Buffer<T>::operator=(Buffer<T> &&other) noexcept {
|
||||
Buffer<T>& Buffer<T>::operator=(Buffer &&other) noexcept {
|
||||
this->m_buffer = other.m_buffer;
|
||||
this->m_size = other.m_size;
|
||||
this->m_type = other.m_type;
|
||||
@@ -154,7 +154,7 @@ namespace hex::gl {
|
||||
glDrawArrays(GL_TRIANGLES, 0, this->m_size);
|
||||
break;
|
||||
case GL_ELEMENT_ARRAY_BUFFER:
|
||||
glDrawElements(GL_TRIANGLES, this->m_size, getType<T>(), nullptr);
|
||||
glDrawElements(GL_TRIANGLES, this->m_size, impl::getType<T>(), nullptr);
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -211,6 +211,9 @@ namespace hex::gl {
|
||||
Texture::Texture(Texture &&other) noexcept {
|
||||
this->m_texture = other.m_texture;
|
||||
other.m_texture = -1;
|
||||
|
||||
this->m_width = other.m_width;
|
||||
this->m_height = other.m_height;
|
||||
}
|
||||
|
||||
Texture& Texture::operator=(Texture &&other) noexcept {
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
|
||||
#include <cstring>
|
||||
#include <string_view>
|
||||
#include <type_traits>
|
||||
|
||||
namespace hex {
|
||||
|
||||
@@ -123,7 +122,8 @@ namespace hex {
|
||||
if (ipsPatch.size() < (5 + 3))
|
||||
return wolv::util::Unexpected(IPSError::InvalidPatchHeader);
|
||||
|
||||
if (std::memcmp(ipsPatch.data(), "PATCH", 5) != 0)
|
||||
const char *header = "PATCH";
|
||||
if (std::memcmp(ipsPatch.data(), header, 5) != 0)
|
||||
return wolv::util::Unexpected(IPSError::InvalidPatchHeader);
|
||||
|
||||
Patches result;
|
||||
@@ -160,7 +160,8 @@ namespace hex {
|
||||
ipsOffset += 1;
|
||||
}
|
||||
|
||||
if (std::memcmp(ipsPatch.data() + ipsOffset, "EOF", 3) == 0)
|
||||
const char *footer = "EOF";
|
||||
if (std::memcmp(ipsPatch.data() + ipsOffset, footer, 3) == 0)
|
||||
foundEOF = true;
|
||||
}
|
||||
|
||||
@@ -174,7 +175,8 @@ namespace hex {
|
||||
if (ipsPatch.size() < (5 + 4))
|
||||
return wolv::util::Unexpected(IPSError::InvalidPatchHeader);
|
||||
|
||||
if (std::memcmp(ipsPatch.data(), "IPS32", 5) != 0)
|
||||
const char *header = "IPS32";
|
||||
if (std::memcmp(ipsPatch.data(), header, 5) != 0)
|
||||
return wolv::util::Unexpected(IPSError::InvalidPatchHeader);
|
||||
|
||||
Patches result;
|
||||
@@ -211,7 +213,8 @@ namespace hex {
|
||||
ipsOffset += 1;
|
||||
}
|
||||
|
||||
if (std::memcmp(ipsPatch.data() + ipsOffset, "EEOF", 4) == 0)
|
||||
const char *footer = "EEOF";
|
||||
if (std::memcmp(ipsPatch.data() + ipsOffset, footer, 4) == 0)
|
||||
foundEEOF = true;
|
||||
}
|
||||
|
||||
|
||||
@@ -21,8 +21,7 @@
|
||||
HANDLE process = GetCurrentProcess();
|
||||
HANDLE thread = GetCurrentThread();
|
||||
|
||||
CONTEXT context;
|
||||
memset(&context, 0, sizeof(CONTEXT));
|
||||
CONTEXT context = {};
|
||||
context.ContextFlags = CONTEXT_FULL;
|
||||
RtlCaptureContext(&context);
|
||||
|
||||
@@ -52,7 +51,7 @@
|
||||
break;
|
||||
|
||||
std::array<char, sizeof(SYMBOL_INFO) + MAX_SYM_NAME * sizeof(TCHAR)> buffer = {};
|
||||
auto symbol = (PSYMBOL_INFO)buffer.data();
|
||||
auto symbol = reinterpret_cast<PSYMBOL_INFO>(buffer.data());
|
||||
symbol->SizeOfStruct = sizeof(SYMBOL_INFO);
|
||||
symbol->MaxNameLen = MAX_SYM_NAME;
|
||||
|
||||
@@ -71,7 +70,7 @@
|
||||
|
||||
DWORD displacementLine = 0;
|
||||
|
||||
u32 lineNumber;
|
||||
u32 lineNumber = 0;
|
||||
const char *fileName;
|
||||
if (SymGetLineFromAddr64(process, stackFrame.AddrPC.Offset, &displacementLine, &line) == TRUE) {
|
||||
lineNumber = line.LineNumber;
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#include <hex/helpers/tar.hpp>
|
||||
#include <hex/helpers/literals.hpp>
|
||||
#include <hex/helpers/fs.hpp>
|
||||
#include <hex/helpers/logger.hpp>
|
||||
#include <hex/helpers/fmt.hpp>
|
||||
|
||||
@@ -97,7 +96,7 @@ namespace hex {
|
||||
return mtar_find(&this->m_ctx, fixedPath.c_str(), &header) == MTAR_ESUCCESS;
|
||||
}
|
||||
|
||||
std::string Tar::getOpenErrorString(){
|
||||
std::string Tar::getOpenErrorString() const {
|
||||
return hex::format("{}: {}", mtar_strerror(this->m_tarOpenErrno), std::strerror(this->m_fileOpenErrno));
|
||||
}
|
||||
|
||||
@@ -119,7 +118,7 @@ namespace hex {
|
||||
std::replace(fixedPath.begin(), fixedPath.end(), '\\', '/');
|
||||
#endif
|
||||
int ret = mtar_find(&this->m_ctx, fixedPath.c_str(), &header);
|
||||
if(ret != MTAR_ESUCCESS){
|
||||
if (ret != MTAR_ESUCCESS){
|
||||
log::debug("Failed to read vector from path {} in tarred file {}: {}",
|
||||
path.string(), this->m_path.string(), mtar_strerror(ret));
|
||||
return {};
|
||||
@@ -162,7 +161,7 @@ namespace hex {
|
||||
this->writeVector(path, { data.begin(), data.end() });
|
||||
}
|
||||
|
||||
static void writeFile(mtar_t *ctx, mtar_header_t *header, const std::fs::path &path) {
|
||||
static void writeFile(mtar_t *ctx, const mtar_header_t *header, const std::fs::path &path) {
|
||||
constexpr static u64 BufferSize = 1_MiB;
|
||||
|
||||
wolv::io::File outputFile(path, wolv::io::File::Mode::Create);
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
#include <hex/helpers/utils.hpp>
|
||||
|
||||
#include <cstdio>
|
||||
#include <codecvt>
|
||||
|
||||
#include <hex/api/imhex_api.hpp>
|
||||
#include <hex/api/event.hpp>
|
||||
@@ -88,7 +87,7 @@ namespace hex {
|
||||
return { };
|
||||
|
||||
// Remove all whitespace
|
||||
string.erase(std::remove_if(string.begin(), string.end(), [](char c) { return std::isspace(c); }), string.end());
|
||||
std::erase_if(string, [](char c) { return std::isspace(c); });
|
||||
|
||||
// Only parse whole bytes
|
||||
if (string.length() % 2 != 0)
|
||||
@@ -257,7 +256,6 @@ namespace hex {
|
||||
|
||||
std::vector<std::string> splitString(const std::string &string, const std::string &delimiter) {
|
||||
size_t start = 0, end = 0;
|
||||
std::string token;
|
||||
std::vector<std::string> res;
|
||||
|
||||
while ((end = string.find(delimiter, start)) != std::string::npos) {
|
||||
@@ -265,7 +263,7 @@ namespace hex {
|
||||
if (start + size > string.length())
|
||||
break;
|
||||
|
||||
token = string.substr(start, end - start);
|
||||
std::string token = string.substr(start, end - start);
|
||||
start = end + delimiter.length();
|
||||
res.push_back(token);
|
||||
}
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
#if defined(OS_LINUX)
|
||||
|
||||
#include<hex/helpers/logger.hpp>
|
||||
#include <hex/helpers/logger.hpp>
|
||||
|
||||
#include<vector>
|
||||
#include<string>
|
||||
#include<unistd.h>
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <unistd.h>
|
||||
|
||||
namespace hex {
|
||||
|
||||
|
||||
@@ -119,7 +119,7 @@ namespace hex::prv {
|
||||
this->markDirty();
|
||||
}
|
||||
|
||||
void Provider::applyOverlays(u64 offset, void *buffer, size_t size) {
|
||||
void Provider::applyOverlays(u64 offset, void *buffer, size_t size) const {
|
||||
for (auto &overlay : this->m_overlays) {
|
||||
auto overlayOffset = overlay->getAddress();
|
||||
auto overlaySize = overlay->getSize();
|
||||
@@ -246,7 +246,7 @@ namespace hex::prv {
|
||||
}
|
||||
|
||||
for (u64 i = 0; i < size; i++) {
|
||||
u8 patch = reinterpret_cast<const u8 *>(buffer)[i];
|
||||
u8 patch = static_cast<const u8 *>(buffer)[i];
|
||||
u8 originalValue = 0x00;
|
||||
this->readRaw((offset + i) - this->getBaseAddress(), &originalValue, sizeof(u8));
|
||||
|
||||
@@ -269,12 +269,12 @@ namespace hex::prv {
|
||||
|
||||
void Provider::undo() {
|
||||
if (canUndo())
|
||||
this->m_currPatches--;
|
||||
--this->m_currPatches;
|
||||
}
|
||||
|
||||
void Provider::redo() {
|
||||
if (canRedo())
|
||||
this->m_currPatches++;
|
||||
++this->m_currPatches;
|
||||
}
|
||||
|
||||
bool Provider::canUndo() const {
|
||||
|
||||
@@ -1,8 +1,6 @@
|
||||
#include<iostream>
|
||||
#include<numeric>
|
||||
#include<string_view>
|
||||
#include<ranges>
|
||||
#include<stdlib.h>
|
||||
#include <numeric>
|
||||
#include <string_view>
|
||||
#include <ranges>
|
||||
|
||||
#include "hex/subcommands/subcommands.hpp"
|
||||
|
||||
@@ -10,6 +8,7 @@
|
||||
#include <hex/api/plugin_manager.hpp>
|
||||
#include <hex/api/imhex_api.hpp>
|
||||
#include <hex/helpers/logger.hpp>
|
||||
#include <hex/helpers/fmt.hpp>
|
||||
|
||||
namespace hex::subcommands {
|
||||
|
||||
@@ -38,7 +37,7 @@ namespace hex::subcommands {
|
||||
std::optional<SubCommand> currentSubCommand = findSubCommand(*argsIter);
|
||||
|
||||
if (currentSubCommand) {
|
||||
argsIter++;
|
||||
argsIter += 1;
|
||||
// If it is a valid subcommand, remove it from the argument list
|
||||
} else {
|
||||
// If no (valid) subcommand was provided, the default one is --open
|
||||
@@ -73,7 +72,7 @@ namespace hex::subcommands {
|
||||
}
|
||||
}
|
||||
|
||||
argsIter++;
|
||||
argsIter += 1;
|
||||
}
|
||||
|
||||
// Save last command to run
|
||||
@@ -109,7 +108,7 @@ namespace hex::subcommands {
|
||||
log::debug("Registered new forward command handler: {}", cmdName);
|
||||
|
||||
ImHexApi::Messaging::impl::getHandlers().insert({ hex::format("command/{}", cmdName), [handler](const std::vector<u8> &eventData){
|
||||
std::string str((const char*) eventData.data(), eventData.size());
|
||||
std::string str(reinterpret_cast<const char *>(eventData.data()), eventData.size());
|
||||
|
||||
std::vector<std::string> args;
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ namespace ImGui {
|
||||
if (width * height * 4 > size)
|
||||
return;
|
||||
|
||||
imageData = (unsigned char*) STBI_MALLOC(size);
|
||||
imageData = static_cast<unsigned char *>(STBI_MALLOC(size));
|
||||
std::memcpy(imageData, buffer, size);
|
||||
this->m_width = width;
|
||||
this->m_height = height;
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
|
||||
#include <functional>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace hex {
|
||||
|
||||
@@ -82,6 +81,6 @@ namespace hex {
|
||||
void View::setFontAtlas(ImFontAtlas *atlas) { s_fontAtlas = atlas; }
|
||||
|
||||
ImFontConfig View::getFontConfig() { return s_fontConfig; }
|
||||
void View::setFontConfig(ImFontConfig config) { s_fontConfig = config; }
|
||||
void View::setFontConfig(ImFontConfig config) { s_fontConfig = std::move(config); }
|
||||
|
||||
}
|
||||
@@ -73,7 +73,7 @@ int launchExecutable() {
|
||||
|
||||
// Get formatted error message from the OS
|
||||
auto errorCode = ::GetLastError();
|
||||
auto errorMessageString = std::system_category().message(errorCode);
|
||||
auto errorMessageString = std::system_category().message(int(errorCode));
|
||||
|
||||
// Generate error message
|
||||
auto errorMessage = fmt::format("Failed to start ImHex:\n\nError code: 0x{:08X}\n\n{}", errorCode, errorMessageString);
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
#pragma once
|
||||
|
||||
#include<string>
|
||||
#include<vector>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include<hex/helpers/types.hpp>
|
||||
#include <hex/helpers/types.hpp>
|
||||
|
||||
/**
|
||||
* Cross-instance (cross-process) messaging system
|
||||
|
||||
@@ -36,7 +36,7 @@ namespace hex {
|
||||
void endNativeWindowFrame();
|
||||
void drawTitleBar();
|
||||
|
||||
void drawTitleBarBorderless();
|
||||
void drawTitleBarBorderless() const;
|
||||
void drawTitleBarBorder();
|
||||
|
||||
void frameBegin();
|
||||
|
||||
@@ -140,7 +140,7 @@ namespace hex::crash {
|
||||
try {
|
||||
std::rethrow_exception(std::current_exception());
|
||||
} catch (std::exception &ex) {
|
||||
std::string exceptionStr = hex::format("{}()::what() -> {}", llvm::itaniumDemangle(typeid(ex).name(), nullptr, nullptr, nullptr), ex.what());
|
||||
std::string exceptionStr = hex::format("{}()::what() -> {}", llvm::itaniumDemangle(typeid(ex).name()), ex.what());
|
||||
|
||||
handleCrash(exceptionStr);
|
||||
log::fatal("Program terminated with uncaught exception: {}", exceptionStr);
|
||||
|
||||
@@ -105,7 +105,7 @@ namespace hex::init {
|
||||
|
||||
// When the task finished, increment the progress bar
|
||||
ON_SCOPE_EXIT {
|
||||
tasksCompleted++;
|
||||
tasksCompleted += 1;
|
||||
this->m_progress = float(tasksCompleted) / this->m_tasks.size();
|
||||
};
|
||||
|
||||
@@ -141,7 +141,7 @@ namespace hex::init {
|
||||
// If the task can be run asynchronously, run it in a separate thread
|
||||
// otherwise run it in this thread and wait for it to finish
|
||||
if (async) {
|
||||
std::thread([runTask]{ runTask(); }).detach();
|
||||
std::thread([runTask = std::move(runTask)]{ runTask(); }).detach();
|
||||
} else {
|
||||
runTask();
|
||||
}
|
||||
@@ -188,15 +188,15 @@ namespace hex::init {
|
||||
const auto hexSpacing = ImVec2(17.4, 15) * scale;
|
||||
const auto hexStart = ImVec2(27, 127) * scale;
|
||||
|
||||
const auto hexCount = ImVec2(13, 7);
|
||||
constexpr auto HexCount = ImVec2(13, 7);
|
||||
|
||||
bool isStart = true;
|
||||
|
||||
color.Value.w *= opacity;
|
||||
|
||||
// Loop over all the bytes on the splash screen
|
||||
for (u32 y = u32(start.y); y < u32(hexCount.y); y += 1) {
|
||||
for (u32 x = u32(start.x); x < u32(hexCount.x); x += 1) {
|
||||
for (u32 y = u32(start.y); y < u32(HexCount.y); y += 1) {
|
||||
for (u32 x = u32(start.x); x < u32(HexCount.x); x += 1) {
|
||||
if (count-- == 0)
|
||||
return;
|
||||
|
||||
@@ -207,7 +207,7 @@ namespace hex::init {
|
||||
drawList->AddRectFilled(pos + ImVec2(0, -hexSpacing.y / 2), pos + hexSize + ImVec2(0, hexSpacing.y / 2), color);
|
||||
|
||||
// Add some extra color on the right if the current byte isn't the last byte, and we didn't reach the right side of the image
|
||||
if (count > 0 && x != u32(hexCount.x) - 1)
|
||||
if (count > 0 && x != u32(HexCount.x) - 1)
|
||||
drawList->AddRectFilled(pos + ImVec2(hexSize.x, -hexSpacing.y / 2), pos + hexSize + ImVec2(hexSpacing.x, hexSpacing.y / 2), color);
|
||||
|
||||
// Add some extra color on the left if this is the first byte we're highlighting
|
||||
|
||||
@@ -49,7 +49,7 @@ namespace hex::init {
|
||||
nlohmann::json releases;
|
||||
try {
|
||||
releases = nlohmann::json::parse(response.getData());
|
||||
} catch (std::exception &e) {
|
||||
} catch (const std::exception &) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -71,7 +71,7 @@ namespace hex::init {
|
||||
|
||||
// Check if there is a telemetry uuid
|
||||
std::string uuid = ContentRegistry::Settings::read("hex.builtin.setting.general", "hex.builtin.setting.general.uuid", "").get<std::string>();
|
||||
if(uuid.empty()) {
|
||||
if (uuid.empty()) {
|
||||
// Generate a new uuid
|
||||
uuid = wolv::hash::generateUUID();
|
||||
// Save
|
||||
@@ -522,9 +522,9 @@ namespace hex::init {
|
||||
|
||||
bool clearOldLogs() {
|
||||
for (const auto &path : fs::getDefaultPaths(fs::ImHexPath::Logs)) {
|
||||
std::vector<std::filesystem::directory_entry> files;
|
||||
|
||||
try {
|
||||
std::vector<std::filesystem::directory_entry> files;
|
||||
|
||||
for (const auto& file : std::filesystem::directory_iterator(path))
|
||||
files.push_back(file);
|
||||
|
||||
@@ -535,11 +535,10 @@ namespace hex::init {
|
||||
return std::filesystem::last_write_time(a) > std::filesystem::last_write_time(b);
|
||||
});
|
||||
|
||||
for (auto it = files.begin() + 10; it != files.end(); it++)
|
||||
for (auto it = files.begin() + 10; it != files.end(); it += 1)
|
||||
std::filesystem::remove(it->path());
|
||||
} catch (std::filesystem::filesystem_error &e) {
|
||||
log::error("Failed to clear old log! {}", e.what());
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -597,8 +596,8 @@ namespace hex::init {
|
||||
// Run all exit tasks, and print to console
|
||||
void runExitTasks() {
|
||||
for (const auto &[name, task, async] : init::getExitTasks()) {
|
||||
task();
|
||||
log::info("Finished exit task {}", name);
|
||||
bool result = task();
|
||||
log::info("Finished exit task {} {}", name, result ? "successfully" : "unsuccessfully");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -238,4 +238,4 @@ int main(int argc, char **argv) {
|
||||
ImHexApi::System::impl::setPortableVersion(isPortableVersion());
|
||||
|
||||
return runImHex();
|
||||
};
|
||||
}
|
||||
|
||||
@@ -8,16 +8,16 @@
|
||||
|
||||
namespace hex::messaging {
|
||||
|
||||
void messageReceived(const std::string &eventName, const std::vector<u8> &eventData) {
|
||||
log::debug("Received event '{}' with size {}", eventName, eventData.size());
|
||||
ImHexApi::Messaging::impl::runHandler(eventName, eventData);
|
||||
void messageReceived(const std::string &eventName, const std::vector<u8> &args) {
|
||||
log::debug("Received event '{}' with size {}", eventName, args.size());
|
||||
ImHexApi::Messaging::impl::runHandler(eventName, args);
|
||||
}
|
||||
|
||||
void setupEvents() {
|
||||
EventManager::subscribe<SendMessageToMainInstance>([](const std::string eventName, const std::vector<u8> &eventData) {
|
||||
EventManager::subscribe<SendMessageToMainInstance>([](const std::string &eventName, const std::vector<u8> &eventData) {
|
||||
log::debug("Forwarding message {} (maybe to us)", eventName);
|
||||
if (ImHexApi::System::isMainInstance()) {
|
||||
EventManager::subscribe<EventImHexStartupFinished>([eventName, eventData](){
|
||||
EventManager::subscribe<EventImHexStartupFinished>([eventName, eventData]{
|
||||
ImHexApi::Messaging::impl::runHandler(eventName, eventData);
|
||||
});
|
||||
} else {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#if defined(OS_LINUX)
|
||||
|
||||
#include<stdexcept>
|
||||
#include <stdexcept>
|
||||
|
||||
#include <hex/helpers/intrinsics.hpp>
|
||||
#include <hex/helpers/logger.hpp>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#if defined(OS_MACOS)
|
||||
|
||||
#include<stdexcept>
|
||||
#include <stdexcept>
|
||||
|
||||
#include <hex/helpers/intrinsics.hpp>
|
||||
#include <hex/helpers/logger.hpp>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#if defined(OS_WEB)
|
||||
|
||||
#include<stdexcept>
|
||||
#include <stdexcept>
|
||||
|
||||
#include <hex/helpers/intrinsics.hpp>
|
||||
#include <hex/helpers/logger.hpp>
|
||||
|
||||
@@ -11,7 +11,7 @@ namespace hex::messaging {
|
||||
|
||||
std::optional<HWND> getImHexWindow() {
|
||||
|
||||
HWND imhexWindow = 0;
|
||||
HWND imhexWindow = nullptr;
|
||||
|
||||
::EnumWindows([](HWND hWnd, LPARAM ret) -> BOOL {
|
||||
// Get the window name
|
||||
@@ -33,11 +33,13 @@ namespace hex::messaging {
|
||||
|
||||
}, reinterpret_cast<LPARAM>(&imhexWindow));
|
||||
|
||||
if (imhexWindow == 0) return { };
|
||||
else return imhexWindow;
|
||||
if (imhexWindow == nullptr)
|
||||
return { };
|
||||
else
|
||||
return imhexWindow;
|
||||
}
|
||||
|
||||
void sendToOtherInstance(const std::string &eventName, const std::vector<u8> &eventData) {
|
||||
void sendToOtherInstance(const std::string &eventName, const std::vector<u8> &args) {
|
||||
log::debug("Sending event {} to another instance (not us)", eventName);
|
||||
|
||||
// Get the window we want to send it to
|
||||
@@ -49,10 +51,10 @@ namespace hex::messaging {
|
||||
std::vector<u8> fulleventData(eventName.begin(), eventName.end());
|
||||
fulleventData.push_back('\0');
|
||||
|
||||
fulleventData.insert(fulleventData.end(), eventData.begin(), eventData.end());
|
||||
fulleventData.insert(fulleventData.end(), args.begin(), args.end());
|
||||
|
||||
u8 *data = &fulleventData[0];
|
||||
DWORD dataSize = static_cast<DWORD>(fulleventData.size());
|
||||
DWORD dataSize = fulleventData.size();
|
||||
|
||||
COPYDATASTRUCT message = {
|
||||
.dwData = 0,
|
||||
|
||||
@@ -42,7 +42,7 @@ namespace hex {
|
||||
log::fatal(message);
|
||||
if (isFileInPath("zenity")) {
|
||||
executeCmd({"zenity", "--error", "--text", message});
|
||||
} else if(isFileInPath("notify-send")) {
|
||||
} else if (isFileInPath("notify-send")) {
|
||||
executeCmd({"notify-send", "-i", "script-error", "Error", message});
|
||||
} // Hopefully one of these commands is installed
|
||||
}
|
||||
|
||||
@@ -9,11 +9,8 @@
|
||||
#include <hex/helpers/utils.hpp>
|
||||
#include <hex/helpers/logger.hpp>
|
||||
|
||||
#include <wolv/utils/string.hpp>
|
||||
|
||||
#include <imgui.h>
|
||||
#include <imgui_internal.h>
|
||||
#include <fonts/codicons_font.h>
|
||||
|
||||
#include <GLFW/glfw3.h>
|
||||
#define GLFW_EXPOSE_NATIVE_WIN32
|
||||
@@ -31,8 +28,6 @@
|
||||
#include <csignal>
|
||||
#include <cstdio>
|
||||
|
||||
#include <imgui_impl_glfw.h>
|
||||
|
||||
namespace hex {
|
||||
|
||||
template<typename T>
|
||||
@@ -44,7 +39,7 @@ namespace hex {
|
||||
|
||||
void nativeErrorMessage(const std::string &message) {
|
||||
log::fatal(message);
|
||||
MessageBox(NULL, message.c_str(), "Error", MB_ICONERROR | MB_OK);
|
||||
MessageBox(nullptr, message.c_str(), "Error", MB_ICONERROR | MB_OK);
|
||||
}
|
||||
|
||||
// Custom Window procedure for receiving OS events
|
||||
@@ -58,7 +53,7 @@ namespace hex {
|
||||
|
||||
ssize_t nullIndex = -1;
|
||||
|
||||
char* messageData = reinterpret_cast<char*>(message->lpData);
|
||||
auto messageData = static_cast<const char*>(message->lpData);
|
||||
size_t messageSize = message->cbData;
|
||||
|
||||
for (size_t i = 0; i < messageSize; i++) {
|
||||
|
||||
@@ -17,9 +17,6 @@
|
||||
|
||||
#include <chrono>
|
||||
#include <csignal>
|
||||
#include <set>
|
||||
#include <thread>
|
||||
#include <cassert>
|
||||
|
||||
#include <romfs/romfs.hpp>
|
||||
|
||||
@@ -117,7 +114,7 @@ namespace hex {
|
||||
});
|
||||
|
||||
// Handle updating the window title
|
||||
EventManager::subscribe<RequestUpdateWindowTitle>(this, [this]() {
|
||||
EventManager::subscribe<RequestUpdateWindowTitle>(this, [this] {
|
||||
std::string title = "ImHex";
|
||||
|
||||
if (ProjectFile::hasPath()) {
|
||||
@@ -247,7 +244,7 @@ namespace hex {
|
||||
}
|
||||
}
|
||||
|
||||
void Window::drawTitleBarBorderless() {
|
||||
void Window::drawTitleBarBorderless() const {
|
||||
auto startX = ImGui::GetCursorPosX();
|
||||
auto titleBarHeight = ImGui::GetCurrentWindow()->MenuBarHeight();
|
||||
auto buttonSize = ImVec2(titleBarHeight * 1.5F, titleBarHeight - 1);
|
||||
@@ -261,8 +258,8 @@ namespace hex {
|
||||
auto &titleBarButtons = ContentRegistry::Interface::impl::getTitleBarButtons();
|
||||
|
||||
// Draw custom title bar buttons
|
||||
if(!titleBarButtons.empty()) {
|
||||
ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * (4 + titleBarButtons.size()));
|
||||
if (!titleBarButtons.empty()) {
|
||||
ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * float(4 + titleBarButtons.size()));
|
||||
for (const auto &[icon, tooltip, callback]: titleBarButtons) {
|
||||
if (ImGui::TitleBarButton(icon.c_str(), buttonSize)) {
|
||||
callback();
|
||||
@@ -311,8 +308,8 @@ namespace hex {
|
||||
auto &titleBarButtons = ContentRegistry::Interface::impl::getTitleBarButtons();
|
||||
|
||||
// Draw custom title bar buttons
|
||||
if(!titleBarButtons.empty()) {
|
||||
ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * (titleBarButtons.size() + 0.5));
|
||||
if (!titleBarButtons.empty()) {
|
||||
ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * (titleBarButtons.size() + 0.5F));
|
||||
for (const auto &[icon, tooltip, callback]: titleBarButtons) {
|
||||
if (ImGui::TitleBarButton(icon.c_str(), buttonSize)) {
|
||||
callback();
|
||||
@@ -528,7 +525,7 @@ namespace hex {
|
||||
|
||||
// Plugin load error popups. These are not translated because they should always be readable, no matter if any localization could be loaded or not
|
||||
{
|
||||
auto drawPluginFolderTable = []() {
|
||||
auto drawPluginFolderTable = [] {
|
||||
ImGui::UnderlinedText("Plugin folders");
|
||||
if (ImGui::BeginTable("plugins", 2, ImGuiTableFlags_Borders | ImGuiTableFlags_RowBg | ImGuiTableFlags_ScrollY | ImGuiTableFlags_SizingFixedFit, ImVec2(0, 100_scaled))) {
|
||||
ImGui::TableSetupScrollFreeze(0, 1);
|
||||
|
||||
@@ -27,7 +27,7 @@ std::string getUpdateUrl(std::string_view versionType, std::string_view operatin
|
||||
return data;
|
||||
}
|
||||
|
||||
std::optional<std::fs::path> downloadUpdate(const std::string &url, const std::string &type) {
|
||||
std::optional<std::fs::path> downloadUpdate(const std::string &url) {
|
||||
// Download the update
|
||||
auto response = hex::HttpRequest("GET", url).downloadFile().get();
|
||||
|
||||
@@ -158,7 +158,7 @@ int main(int argc, char **argv) {
|
||||
hex::log::info("Update URL found: {}", updateUrl);
|
||||
|
||||
// Download the update file
|
||||
auto updatePath = downloadUpdate(updateUrl, updateType);
|
||||
auto updatePath = downloadUpdate(updateUrl);
|
||||
if (!updatePath.has_value())
|
||||
return EXIT_FAILURE;
|
||||
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
#pragma once
|
||||
|
||||
namespace hex::plugin::builtin {
|
||||
|
||||
void openProject();
|
||||
void saveProject();
|
||||
void saveProjectAs();
|
||||
|
||||
}
|
||||
|
||||
@@ -15,14 +15,14 @@
|
||||
|
||||
namespace hex {
|
||||
|
||||
namespace {
|
||||
namespace impl {
|
||||
|
||||
int IntegerAxisFormatter(double value, char* buffer, int size, void *userData) {
|
||||
inline int IntegerAxisFormatter(double value, char* buffer, int size, void *userData) {
|
||||
u64 integer = static_cast<u64>(value);
|
||||
return snprintf(buffer, size, static_cast<const char*>(userData), integer);
|
||||
}
|
||||
|
||||
std::vector<u8> getSampleSelection(prv::Provider *provider, u64 address, size_t size, size_t sampleSize) {
|
||||
inline std::vector<u8> getSampleSelection(prv::Provider *provider, u64 address, size_t size, size_t sampleSize) {
|
||||
const size_t sequenceCount = std::ceil(std::sqrt(sampleSize));
|
||||
|
||||
std::vector<u8> buffer;
|
||||
@@ -60,7 +60,7 @@ namespace hex {
|
||||
return buffer;
|
||||
}
|
||||
|
||||
std::vector<u8> getSampleSelection(const std::vector<u8> &inputBuffer, size_t sampleSize) {
|
||||
inline std::vector<u8> getSampleSelection(const std::vector<u8> &inputBuffer, size_t sampleSize) {
|
||||
const size_t sequenceCount = std::ceil(std::sqrt(sampleSize));
|
||||
|
||||
std::vector<u8> buffer;
|
||||
@@ -77,7 +77,7 @@ namespace hex {
|
||||
|
||||
std::vector<u8> sequence;
|
||||
sequence.reserve(sampleSize);
|
||||
std::copy(inputBuffer.begin() + offset, inputBuffer.begin() + offset + std::min<size_t>(sequenceCount, inputBuffer.size() - offset), std::back_inserter(sequence));
|
||||
std::copy_n(inputBuffer.begin() + offset, std::min<size_t>(sequenceCount, inputBuffer.size() - offset), std::back_inserter(sequence));
|
||||
|
||||
orderedData.insert({ offset, sequence });
|
||||
}
|
||||
@@ -101,7 +101,7 @@ namespace hex {
|
||||
|
||||
class DiagramDigram {
|
||||
public:
|
||||
DiagramDigram(size_t sampleSize = 0x9000) : m_sampleSize(sampleSize) { }
|
||||
explicit DiagramDigram(size_t sampleSize = 0x9000) : m_sampleSize(sampleSize) { }
|
||||
|
||||
void draw(ImVec2 size) {
|
||||
ImGui::PushStyleColor(ImGuiCol_ChildBg, ImU32(ImColor(0, 0, 0)));
|
||||
@@ -128,14 +128,14 @@ namespace hex {
|
||||
|
||||
void process(prv::Provider *provider, u64 address, size_t size) {
|
||||
this->m_processing = true;
|
||||
this->m_buffer = getSampleSelection(provider, address, size, this->m_sampleSize);
|
||||
this->m_buffer = impl::getSampleSelection(provider, address, size, this->m_sampleSize);
|
||||
processImpl();
|
||||
this->m_processing = false;
|
||||
}
|
||||
|
||||
void process(const std::vector<u8> &buffer) {
|
||||
this->m_processing = true;
|
||||
this->m_buffer = getSampleSelection(buffer, this->m_sampleSize);
|
||||
this->m_buffer = impl::getSampleSelection(buffer, this->m_sampleSize);
|
||||
processImpl();
|
||||
this->m_processing = false;
|
||||
}
|
||||
@@ -154,7 +154,7 @@ namespace hex {
|
||||
this->m_buffer[this->m_byteCount] = byte;
|
||||
++this->m_byteCount;
|
||||
if (this->m_byteCount == this->m_fileSize) {
|
||||
this->m_buffer = getSampleSelection(this->m_buffer, this->m_sampleSize);
|
||||
this->m_buffer = impl::getSampleSelection(this->m_buffer, this->m_sampleSize);
|
||||
processImpl();
|
||||
this->m_processing = false;
|
||||
}
|
||||
@@ -181,12 +181,12 @@ namespace hex {
|
||||
}
|
||||
|
||||
private:
|
||||
size_t m_sampleSize;
|
||||
size_t m_sampleSize = 0;
|
||||
|
||||
// The number of bytes processed and the size of
|
||||
// the file to analyze (useful for iterative analysis)
|
||||
u64 m_byteCount;
|
||||
u64 m_fileSize;
|
||||
u64 m_byteCount = 0;
|
||||
u64 m_fileSize = 0;
|
||||
std::vector<u8> m_buffer;
|
||||
std::vector<float> m_glowBuffer;
|
||||
float m_opacity = 0.0F;
|
||||
@@ -196,7 +196,7 @@ namespace hex {
|
||||
|
||||
class DiagramLayeredDistribution {
|
||||
public:
|
||||
DiagramLayeredDistribution(size_t sampleSize = 0x9000) : m_sampleSize(sampleSize) { }
|
||||
explicit DiagramLayeredDistribution(size_t sampleSize = 0x9000) : m_sampleSize(sampleSize) { }
|
||||
|
||||
void draw(ImVec2 size) {
|
||||
ImGui::PushStyleColor(ImGuiCol_ChildBg, ImU32(ImColor(0, 0, 0)));
|
||||
@@ -223,14 +223,14 @@ namespace hex {
|
||||
|
||||
void process(prv::Provider *provider, u64 address, size_t size) {
|
||||
this->m_processing = true;
|
||||
this->m_buffer = getSampleSelection(provider, address, size, this->m_sampleSize);
|
||||
this->m_buffer = impl::getSampleSelection(provider, address, size, this->m_sampleSize);
|
||||
processImpl();
|
||||
this->m_processing = false;
|
||||
}
|
||||
|
||||
void process(const std::vector<u8> &buffer) {
|
||||
this->m_processing = true;
|
||||
this->m_buffer = getSampleSelection(buffer, this->m_sampleSize);
|
||||
this->m_buffer = impl::getSampleSelection(buffer, this->m_sampleSize);
|
||||
processImpl();
|
||||
this->m_processing = false;
|
||||
}
|
||||
@@ -249,7 +249,7 @@ namespace hex {
|
||||
this->m_buffer[this->m_byteCount] = byte;
|
||||
++this->m_byteCount;
|
||||
if (this->m_byteCount == this->m_fileSize) {
|
||||
this->m_buffer = getSampleSelection(this->m_buffer, this->m_sampleSize);
|
||||
this->m_buffer = impl::getSampleSelection(this->m_buffer, this->m_sampleSize);
|
||||
processImpl();
|
||||
this->m_processing = false;
|
||||
}
|
||||
@@ -274,12 +274,12 @@ namespace hex {
|
||||
this->m_opacity = (log10(float(this->m_sampleSize)) / log10(float(m_highestCount))) / 10.0F;
|
||||
}
|
||||
private:
|
||||
size_t m_sampleSize;
|
||||
size_t m_sampleSize = 0;
|
||||
|
||||
// The number of bytes processed and the size of
|
||||
// the file to analyze (useful for iterative analysis)
|
||||
u64 m_byteCount;
|
||||
u64 m_fileSize;
|
||||
u64 m_byteCount = 0;
|
||||
u64 m_fileSize = 0;
|
||||
|
||||
std::vector<u8> m_buffer;
|
||||
std::vector<float> m_glowBuffer;
|
||||
@@ -290,7 +290,7 @@ namespace hex {
|
||||
|
||||
class DiagramChunkBasedEntropyAnalysis {
|
||||
public:
|
||||
DiagramChunkBasedEntropyAnalysis(u64 blockSize = 256, size_t sampleSize = 0x1000) : m_blockSize(blockSize), m_sampleSize(sampleSize) { }
|
||||
explicit DiagramChunkBasedEntropyAnalysis(u64 blockSize = 256, size_t sampleSize = 0x1000) : m_blockSize(blockSize), m_sampleSize(sampleSize) { }
|
||||
|
||||
void draw(ImVec2 size, ImPlotFlags flags, bool updateHandle = false) {
|
||||
|
||||
@@ -298,7 +298,7 @@ namespace hex {
|
||||
ImPlot::SetupAxes("hex.builtin.common.address"_lang, "hex.builtin.view.information.entropy"_lang,
|
||||
ImPlotAxisFlags_Lock | ImPlotAxisFlags_NoHighlight | ImPlotAxisFlags_NoSideSwitch,
|
||||
ImPlotAxisFlags_Lock | ImPlotAxisFlags_NoHighlight | ImPlotAxisFlags_NoSideSwitch);
|
||||
ImPlot::SetupAxisFormat(ImAxis_X1, IntegerAxisFormatter, (void*)"0x%04llX");
|
||||
ImPlot::SetupAxisFormat(ImAxis_X1, impl::IntegerAxisFormatter, (void*)("0x%04llX"));
|
||||
ImPlot::SetupMouseText(ImPlotLocation_NorthEast);
|
||||
|
||||
// Set the axis limit to [first block : last block]
|
||||
@@ -358,7 +358,7 @@ namespace hex {
|
||||
this->m_processing = false;
|
||||
}
|
||||
|
||||
void process(std::vector<u8> buffer, u64 chunkSize) {
|
||||
void process(const std::vector<u8> &buffer, u64 chunkSize) {
|
||||
this->m_processing = true;
|
||||
|
||||
// Update attributes (use buffer size as end address)
|
||||
@@ -428,11 +428,11 @@ namespace hex {
|
||||
|
||||
// Method used to compute the entropy of a block of size `blockSize`
|
||||
// using the byte occurrences from `valueCounts` array.
|
||||
double calculateEntropy(std::array<ImU64, 256> &valueCounts, size_t blockSize) {
|
||||
double calculateEntropy(const std::array<ImU64, 256> &valueCounts, size_t blockSize) const {
|
||||
double entropy = 0;
|
||||
|
||||
u8 processedValueCount = 0;
|
||||
for (auto count : valueCounts) {
|
||||
for (const auto count : valueCounts) {
|
||||
if (count == 0) [[unlikely]]
|
||||
continue;
|
||||
|
||||
@@ -482,12 +482,12 @@ namespace hex {
|
||||
}
|
||||
|
||||
// Return the number of blocks that have been processed
|
||||
u64 getSize() {
|
||||
u64 getSize() const {
|
||||
return this->m_yBlockEntropySampled.size();
|
||||
}
|
||||
|
||||
// Return the size of the chunk used for this analysis
|
||||
u64 getChunkSize() {
|
||||
u64 getChunkSize() const {
|
||||
return this->m_chunkSize;
|
||||
}
|
||||
|
||||
@@ -497,7 +497,7 @@ namespace hex {
|
||||
|
||||
private:
|
||||
// Private method used to factorize the process public method
|
||||
void processImpl(std::vector<u8> bytes) {
|
||||
void processImpl(const std::vector<u8> &bytes) {
|
||||
this->m_blockValueCounts = { 0 };
|
||||
|
||||
// Reset and resize the array
|
||||
@@ -586,6 +586,7 @@ namespace hex {
|
||||
|
||||
class DiagramByteDistribution {
|
||||
public:
|
||||
DiagramByteDistribution() = default;
|
||||
|
||||
void draw(ImVec2 size, ImPlotFlags flags) {
|
||||
|
||||
@@ -595,7 +596,7 @@ namespace hex {
|
||||
ImPlotAxisFlags_Lock | ImPlotAxisFlags_NoHighlight | ImPlotAxisFlags_NoSideSwitch);
|
||||
ImPlot::SetupAxisScale(ImAxis_Y1, ImPlotScale_Log10);
|
||||
ImPlot::SetupAxesLimits(-1, 256, 1, double(*std::max_element(this->m_valueCounts.begin(), this->m_valueCounts.end())) * 1.1F, ImGuiCond_Always);
|
||||
ImPlot::SetupAxisFormat(ImAxis_X1, IntegerAxisFormatter, (void*)"0x%02llX");
|
||||
ImPlot::SetupAxisFormat(ImAxis_X1, impl::IntegerAxisFormatter, (void*)("0x%02llX"));
|
||||
ImPlot::SetupAxisTicks(ImAxis_X1, 0, 255, 17);
|
||||
ImPlot::SetupMouseText(ImPlotLocation_NorthEast);
|
||||
|
||||
@@ -626,7 +627,7 @@ namespace hex {
|
||||
this->m_processing = false;
|
||||
}
|
||||
|
||||
void process(std::vector<u8> buffer) {
|
||||
void process(const std::vector<u8> &buffer) {
|
||||
this->m_processing = true;
|
||||
|
||||
// Update attributes
|
||||
@@ -659,7 +660,7 @@ namespace hex {
|
||||
|
||||
private:
|
||||
// Private method used to factorize the process public method
|
||||
void processImpl(std::vector<u8> bytes) {
|
||||
void processImpl(const std::vector<u8> &bytes) {
|
||||
// Reset the array
|
||||
this->m_valueCounts.fill(0);
|
||||
// Loop over each byte of the file (or a part of it)
|
||||
@@ -670,8 +671,8 @@ namespace hex {
|
||||
|
||||
private:
|
||||
// Variables used to store the parameters to process
|
||||
u64 m_startAddress;
|
||||
u64 m_endAddress;
|
||||
u64 m_startAddress = 0;
|
||||
u64 m_endAddress = 0;
|
||||
|
||||
// Hold the result of the byte distribution analysis
|
||||
std::array<ImU64, 256> m_valueCounts;
|
||||
@@ -680,7 +681,7 @@ namespace hex {
|
||||
|
||||
class DiagramByteTypesDistribution {
|
||||
public:
|
||||
DiagramByteTypesDistribution(u64 blockSize = 256, size_t sampleSize = 0x1000) : m_blockSize(blockSize), m_sampleSize(sampleSize){ }
|
||||
explicit DiagramByteTypesDistribution(u64 blockSize = 256, size_t sampleSize = 0x1000) : m_blockSize(blockSize), m_sampleSize(sampleSize){ }
|
||||
|
||||
void draw(ImVec2 size, ImPlotFlags flags, bool updateHandle = false) {
|
||||
// Draw the result of the analysis
|
||||
@@ -695,7 +696,7 @@ namespace hex {
|
||||
100.1F,
|
||||
ImGuiCond_Always);
|
||||
ImPlot::SetupLegend(ImPlotLocation_South, ImPlotLegendFlags_Horizontal | ImPlotLegendFlags_Outside);
|
||||
ImPlot::SetupAxisFormat(ImAxis_X1, IntegerAxisFormatter, (void*)"0x%04llX");
|
||||
ImPlot::SetupAxisFormat(ImAxis_X1, impl::IntegerAxisFormatter, (void*)("0x%04llX"));
|
||||
ImPlot::SetupMouseText(ImPlotLocation_NorthEast);
|
||||
|
||||
constexpr static std::array Names = { "iscntrl", "isprint", "isspace", "isblank",
|
||||
@@ -751,7 +752,7 @@ namespace hex {
|
||||
this->m_processing = false;
|
||||
}
|
||||
|
||||
void process(std::vector<u8> buffer, u64 baseAddress, u64 fileSize) {
|
||||
void process(const std::vector<u8> &buffer, u64 baseAddress, u64 fileSize) {
|
||||
this->m_processing = true;
|
||||
|
||||
// Update attributes
|
||||
@@ -831,7 +832,7 @@ namespace hex {
|
||||
}
|
||||
|
||||
private:
|
||||
std::array<float, 12> calculateTypeDistribution(std::array<ImU64, 256> &valueCounts, size_t blockSize) {
|
||||
std::array<float, 12> calculateTypeDistribution(const std::array<ImU64, 256> &valueCounts, size_t blockSize) const {
|
||||
std::array<ImU64, 12> counts = {};
|
||||
|
||||
for (u16 value = 0x00; value < u16(valueCounts.size()); value++) {
|
||||
@@ -874,7 +875,7 @@ namespace hex {
|
||||
}
|
||||
|
||||
// Private method used to factorize the process public method
|
||||
void processImpl(std::vector<u8> bytes) {
|
||||
void processImpl(const std::vector<u8> &bytes) {
|
||||
this->m_blockValueCounts = { 0 };
|
||||
|
||||
this->m_yBlockTypeDistributions.fill({});
|
||||
@@ -924,27 +925,27 @@ namespace hex {
|
||||
// Variables used to store the parameters to process
|
||||
|
||||
// The size of the block we are considering for the analysis
|
||||
u64 m_blockSize;
|
||||
u64 m_startAddress;
|
||||
u64 m_endAddress;
|
||||
u64 m_blockSize = 0;
|
||||
u64 m_startAddress = 0;
|
||||
u64 m_endAddress = 0;
|
||||
// Start / size of the file
|
||||
u64 m_baseAddress;
|
||||
u64 m_fileSize;
|
||||
u64 m_baseAddress = 0;
|
||||
u64 m_fileSize = 0;
|
||||
|
||||
// Position of the handle inside the plot
|
||||
double m_handlePosition = 0.0;
|
||||
|
||||
// Hold the number of blocks that have been processed
|
||||
// during the chunk-based entropy analysis
|
||||
u64 m_blockCount;
|
||||
u64 m_blockCount = 0;
|
||||
|
||||
// Hold the number of bytes that have been processed
|
||||
// during the analysis (useful for the iterative analysis)
|
||||
u64 m_byteCount;
|
||||
u64 m_byteCount = 0;
|
||||
|
||||
// Sampling size, number of elements displayed in the plot,
|
||||
// avoid showing to many data because it decreased the frame rate
|
||||
size_t m_sampleSize;
|
||||
size_t m_sampleSize = 0;
|
||||
|
||||
// Array used to hold the occurrences of each byte
|
||||
// (useful for the iterative analysis)
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <content/popups/popup_notification.hpp>
|
||||
|
||||
namespace hex::plugin::builtin {
|
||||
|
||||
void showError(const std::string& message);
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex/ui/popup.hpp>
|
||||
|
||||
#include <hex/ui/imgui_imhex_extensions.h>
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex/ui/popup.hpp>
|
||||
|
||||
#include <hex/api/localization.hpp>
|
||||
|
||||
@@ -51,7 +51,7 @@ namespace hex::plugin::builtin {
|
||||
class PopupInfo : public impl::PopupNotification<PopupInfo> {
|
||||
public:
|
||||
explicit PopupInfo(std::string message)
|
||||
: PopupNotification("hex.builtin.common.info", std::move(message), [this]() {
|
||||
: PopupNotification("hex.builtin.common.info", std::move(message), [this] {
|
||||
Popup::close();
|
||||
}) { }
|
||||
};
|
||||
@@ -59,7 +59,7 @@ namespace hex::plugin::builtin {
|
||||
class PopupWarning : public impl::PopupNotification<PopupWarning> {
|
||||
public:
|
||||
explicit PopupWarning(std::string message)
|
||||
: PopupNotification("hex.builtin.common.warning", std::move(message), [this]() {
|
||||
: PopupNotification("hex.builtin.common.warning", std::move(message), [this] {
|
||||
Popup::close();
|
||||
}) { }
|
||||
};
|
||||
@@ -67,7 +67,7 @@ namespace hex::plugin::builtin {
|
||||
class PopupError : public impl::PopupNotification<PopupError> {
|
||||
public:
|
||||
explicit PopupError(std::string message)
|
||||
: PopupNotification("hex.builtin.common.error", std::move(message), [this]() {
|
||||
: PopupNotification("hex.builtin.common.error", std::move(message), [this] {
|
||||
Popup::close();
|
||||
}) { }
|
||||
};
|
||||
@@ -75,7 +75,7 @@ namespace hex::plugin::builtin {
|
||||
class PopupFatal : public impl::PopupNotification<PopupFatal> {
|
||||
public:
|
||||
explicit PopupFatal(std::string message)
|
||||
: PopupNotification("hex.builtin.common.fatal", std::move(message), [this]() {
|
||||
: PopupNotification("hex.builtin.common.fatal", std::move(message), [this] {
|
||||
ImHexApi::System::closeImHex();
|
||||
Popup::close();
|
||||
}) { }
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex/ui/popup.hpp>
|
||||
|
||||
#include <hex/api/localization.hpp>
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex/ui/popup.hpp>
|
||||
|
||||
#include <hex/api/localization.hpp>
|
||||
|
||||
#include <functional>
|
||||
#include <string>
|
||||
|
||||
namespace hex::plugin::builtin {
|
||||
|
||||
@@ -1,10 +1,11 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex/ui/popup.hpp>
|
||||
|
||||
#include <hex/api/localization.hpp>
|
||||
|
||||
#include <wolv/hash/uuid.hpp>
|
||||
|
||||
#include <functional>
|
||||
#include <string>
|
||||
|
||||
namespace hex::plugin::builtin {
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex/ui/popup.hpp>
|
||||
|
||||
#include <hex/api/localization.hpp>
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <hex/ui/popup.hpp>
|
||||
|
||||
#include <hex/api/localization.hpp>
|
||||
|
||||
@@ -16,7 +16,7 @@ namespace hex::plugin::builtin {
|
||||
|
||||
class DiskProvider : public hex::prv::Provider {
|
||||
public:
|
||||
DiskProvider();
|
||||
DiskProvider() = default;
|
||||
~DiskProvider() override = default;
|
||||
|
||||
[[nodiscard]] bool isAvailable() const override;
|
||||
|
||||
@@ -44,7 +44,7 @@ namespace hex::plugin::builtin {
|
||||
protected:
|
||||
bool m_dataValid = false;
|
||||
size_t m_dataSize = 0x00;
|
||||
wolv::container::IntervalTree<std::vector<u8>, u64> m_data;
|
||||
wolv::container::IntervalTree<std::vector<u8>> m_data;
|
||||
|
||||
std::fs::path m_sourceFilePath;
|
||||
};
|
||||
|
||||
@@ -20,9 +20,6 @@ namespace hex::plugin::builtin {
|
||||
}
|
||||
|
||||
bool handleFilePicker() override;
|
||||
|
||||
private:
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
@@ -10,7 +10,7 @@ namespace hex::plugin::builtin {
|
||||
class ViewProvider : public hex::prv::Provider {
|
||||
public:
|
||||
explicit ViewProvider() {
|
||||
EventManager::subscribe<EventProviderClosing>(this, [this](prv::Provider *provider, bool*) {
|
||||
EventManager::subscribe<EventProviderClosing>(this, [this](const prv::Provider *provider, bool*) {
|
||||
if (this->m_provider == provider)
|
||||
ImHexApi::Provider::remove(this, false);
|
||||
});
|
||||
|
||||
@@ -1,8 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <atomic>
|
||||
#include <list>
|
||||
|
||||
#include <nlohmann/json.hpp>
|
||||
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user