[lldb] upgrade HandleFrameFormatVariable callees to llvm::Expected (#144731)
Upgrade the callees of `HandleFrameFormatVariable` (`GetDemangledTemplateArguments`, etc), to return a `llvm::Expected` instead of an `std::optional`. This patch also bundles the logic of validating the demangled name and information into a single reusable function to reduce code duplication.
This commit is contained in:
@@ -71,27 +71,28 @@ struct DemangledNameInfo {
|
||||
|
||||
/// Returns \c true if this object holds a valid basename range.
|
||||
bool hasBasename() const {
|
||||
// A function always has a name.
|
||||
return BasenameRange.second > BasenameRange.first;
|
||||
}
|
||||
|
||||
/// Returns \c true if this object holds a valid scope range.
|
||||
bool hasScope() const { return ScopeRange.second > ScopeRange.first; }
|
||||
bool hasScope() const { return ScopeRange.second >= ScopeRange.first; }
|
||||
|
||||
/// Returns \c true if this object holds a valid arguments range.
|
||||
bool hasArguments() const {
|
||||
return ArgumentsRange.second > ArgumentsRange.first;
|
||||
return ArgumentsRange.second >= ArgumentsRange.first;
|
||||
}
|
||||
|
||||
/// Returns \c true if this object holds a valid qualifiers range.
|
||||
bool hasQualifiers() const {
|
||||
return QualifiersRange.second > QualifiersRange.first;
|
||||
return QualifiersRange.second >= QualifiersRange.first;
|
||||
}
|
||||
|
||||
/// Returns \c true if this object holds a valid prefix range.
|
||||
bool hasPrefix() const { return PrefixRange.second > PrefixRange.first; }
|
||||
bool hasPrefix() const { return PrefixRange.second >= PrefixRange.first; }
|
||||
|
||||
/// Returns \c true if this object holds a valid suffix range.
|
||||
bool hasSuffix() const { return SuffixRange.second > SuffixRange.first; }
|
||||
bool hasSuffix() const { return SuffixRange.second >= SuffixRange.first; }
|
||||
};
|
||||
|
||||
/// An OutputBuffer which keeps a record of where certain parts of a
|
||||
|
||||
@@ -236,199 +236,158 @@ static bool PrettyPrintFunctionNameWithArgs(Stream &out_stream,
|
||||
return true;
|
||||
}
|
||||
|
||||
static std::optional<llvm::StringRef>
|
||||
static llvm::Expected<std::pair<llvm::StringRef, DemangledNameInfo>>
|
||||
GetAndValidateInfo(const SymbolContext &sc) {
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
return llvm::createStringError("Function does not have a mangled name.");
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return llvm::createStringError(
|
||||
"Function '%s' does not have a demangled name.",
|
||||
mangled.GetMangledName().AsCString(""));
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return llvm::createStringError(
|
||||
"Function '%s' does not have demangled info.", demangled_name.data());
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return llvm::createStringError(
|
||||
"DemangledInfo for '%s does not have basename range.",
|
||||
demangled_name.data());
|
||||
|
||||
return std::make_pair(demangled_name, *info);
|
||||
}
|
||||
|
||||
static llvm::Expected<llvm::StringRef>
|
||||
GetDemangledBasename(const SymbolContext &sc) {
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
return std::nullopt;
|
||||
auto info_or_err = GetAndValidateInfo(sc);
|
||||
if (!info_or_err)
|
||||
return info_or_err.takeError();
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return std::nullopt;
|
||||
auto [demangled_name, info] = *info_or_err;
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return std::nullopt;
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return std::nullopt;
|
||||
|
||||
return demangled_name.slice(info->BasenameRange.first,
|
||||
info->BasenameRange.second);
|
||||
return demangled_name.slice(info.BasenameRange.first,
|
||||
info.BasenameRange.second);
|
||||
}
|
||||
|
||||
static std::optional<llvm::StringRef>
|
||||
static llvm::Expected<llvm::StringRef>
|
||||
GetDemangledTemplateArguments(const SymbolContext &sc) {
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
return std::nullopt;
|
||||
auto info_or_err = GetAndValidateInfo(sc);
|
||||
if (!info_or_err)
|
||||
return info_or_err.takeError();
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return std::nullopt;
|
||||
auto [demangled_name, info] = *info_or_err;
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return std::nullopt;
|
||||
if (info.ArgumentsRange.first < info.BasenameRange.second)
|
||||
return llvm::createStringError("Arguments range for '%s' is invalid.",
|
||||
demangled_name.data());
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return std::nullopt;
|
||||
|
||||
if (info->ArgumentsRange.first < info->BasenameRange.second)
|
||||
return std::nullopt;
|
||||
|
||||
return demangled_name.slice(info->BasenameRange.second,
|
||||
info->ArgumentsRange.first);
|
||||
return demangled_name.slice(info.BasenameRange.second,
|
||||
info.ArgumentsRange.first);
|
||||
}
|
||||
|
||||
static std::optional<llvm::StringRef>
|
||||
static llvm::Expected<llvm::StringRef>
|
||||
GetDemangledReturnTypeLHS(const SymbolContext &sc) {
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
return std::nullopt;
|
||||
auto info_or_err = GetAndValidateInfo(sc);
|
||||
if (!info_or_err)
|
||||
return info_or_err.takeError();
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return std::nullopt;
|
||||
auto [demangled_name, info] = *info_or_err;
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return std::nullopt;
|
||||
if (info.ScopeRange.first >= demangled_name.size())
|
||||
return llvm::createStringError(
|
||||
"Scope range for '%s' LHS return type is invalid.",
|
||||
demangled_name.data());
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return std::nullopt;
|
||||
|
||||
if (info->ScopeRange.first >= demangled_name.size())
|
||||
return std::nullopt;
|
||||
|
||||
return demangled_name.substr(0, info->ScopeRange.first);
|
||||
return demangled_name.substr(0, info.ScopeRange.first);
|
||||
}
|
||||
|
||||
static std::optional<llvm::StringRef>
|
||||
static llvm::Expected<llvm::StringRef>
|
||||
GetDemangledFunctionQualifiers(const SymbolContext &sc) {
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
return std::nullopt;
|
||||
auto info_or_err = GetAndValidateInfo(sc);
|
||||
if (!info_or_err)
|
||||
return info_or_err.takeError();
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return std::nullopt;
|
||||
auto [demangled_name, info] = *info_or_err;
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return std::nullopt;
|
||||
if (!info.hasQualifiers())
|
||||
return llvm::createStringError("Qualifiers range for '%s' is invalid.",
|
||||
demangled_name.data());
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return std::nullopt;
|
||||
|
||||
if (info->QualifiersRange.second < info->QualifiersRange.first)
|
||||
return std::nullopt;
|
||||
|
||||
return demangled_name.slice(info->QualifiersRange.first,
|
||||
info->QualifiersRange.second);
|
||||
return demangled_name.slice(info.QualifiersRange.first,
|
||||
info.QualifiersRange.second);
|
||||
}
|
||||
|
||||
static std::optional<llvm::StringRef>
|
||||
static llvm::Expected<llvm::StringRef>
|
||||
GetDemangledReturnTypeRHS(const SymbolContext &sc) {
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
return std::nullopt;
|
||||
auto info_or_err = GetAndValidateInfo(sc);
|
||||
if (!info_or_err)
|
||||
return info_or_err.takeError();
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return std::nullopt;
|
||||
auto [demangled_name, info] = *info_or_err;
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return std::nullopt;
|
||||
if (info.QualifiersRange.first < info.ArgumentsRange.second)
|
||||
return llvm::createStringError(
|
||||
"Qualifiers range for '%s' RHS return type is invalid.",
|
||||
demangled_name.data());
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return std::nullopt;
|
||||
|
||||
if (info->QualifiersRange.first < info->ArgumentsRange.second)
|
||||
return std::nullopt;
|
||||
|
||||
return demangled_name.slice(info->ArgumentsRange.second,
|
||||
info->QualifiersRange.first);
|
||||
return demangled_name.slice(info.ArgumentsRange.second,
|
||||
info.QualifiersRange.first);
|
||||
}
|
||||
|
||||
static std::optional<llvm::StringRef>
|
||||
static llvm::Expected<llvm::StringRef>
|
||||
GetDemangledScope(const SymbolContext &sc) {
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
return std::nullopt;
|
||||
auto info_or_err = GetAndValidateInfo(sc);
|
||||
if (!info_or_err)
|
||||
return info_or_err.takeError();
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return std::nullopt;
|
||||
auto [demangled_name, info] = *info_or_err;
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return std::nullopt;
|
||||
if (!info.hasScope())
|
||||
return llvm::createStringError("Scope range for '%s' is invalid.",
|
||||
demangled_name.data());
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return std::nullopt;
|
||||
|
||||
if (info->ScopeRange.second < info->ScopeRange.first)
|
||||
return std::nullopt;
|
||||
|
||||
return demangled_name.slice(info->ScopeRange.first, info->ScopeRange.second);
|
||||
return demangled_name.slice(info.ScopeRange.first, info.ScopeRange.second);
|
||||
}
|
||||
|
||||
/// Handles anything printed after the FunctionEncoding ItaniumDemangle
|
||||
/// node. Most notably the DotSUffix node.
|
||||
static std::optional<llvm::StringRef>
|
||||
static llvm::Expected<llvm::StringRef>
|
||||
GetDemangledFunctionSuffix(const SymbolContext &sc) {
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
return std::nullopt;
|
||||
auto info_or_err = GetAndValidateInfo(sc);
|
||||
if (!info_or_err)
|
||||
return info_or_err.takeError();
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return std::nullopt;
|
||||
auto [demangled_name, info] = *info_or_err;
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return std::nullopt;
|
||||
if (!info.hasSuffix())
|
||||
return llvm::createStringError("Suffix range for '%s' is invalid.",
|
||||
demangled_name.data());
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return std::nullopt;
|
||||
|
||||
return demangled_name.slice(info->SuffixRange.first,
|
||||
info->SuffixRange.second);
|
||||
return demangled_name.slice(info.SuffixRange.first, info.SuffixRange.second);
|
||||
}
|
||||
|
||||
static bool PrintDemangledArgumentList(Stream &s, const SymbolContext &sc) {
|
||||
assert(sc.symbol);
|
||||
|
||||
Mangled mangled = sc.GetPossiblyInlinedFunctionName();
|
||||
if (!mangled)
|
||||
auto info_or_err = GetAndValidateInfo(sc);
|
||||
if (!info_or_err) {
|
||||
LLDB_LOG_ERROR(
|
||||
GetLog(LLDBLog::Language), info_or_err.takeError(),
|
||||
"Failed to handle ${{function.basename}} frame-format variable: {0}");
|
||||
return false;
|
||||
}
|
||||
auto [demangled_name, info] = *info_or_err;
|
||||
|
||||
if (!info.hasArguments())
|
||||
return false;
|
||||
|
||||
auto demangled_name = mangled.GetDemangledName().GetStringRef();
|
||||
if (demangled_name.empty())
|
||||
return false;
|
||||
|
||||
const std::optional<DemangledNameInfo> &info = mangled.GetDemangledInfo();
|
||||
if (!info)
|
||||
return false;
|
||||
|
||||
// Function without a basename is nonsense.
|
||||
if (!info->hasBasename())
|
||||
return false;
|
||||
|
||||
if (info->ArgumentsRange.second < info->ArgumentsRange.first)
|
||||
return false;
|
||||
|
||||
s << demangled_name.slice(info->ArgumentsRange.first,
|
||||
info->ArgumentsRange.second);
|
||||
s << demangled_name.slice(info.ArgumentsRange.first,
|
||||
info.ArgumentsRange.second);
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -1954,32 +1913,44 @@ bool CPlusPlusLanguage::HandleFrameFormatVariable(
|
||||
FormatEntity::Entry::Type type, Stream &s) {
|
||||
switch (type) {
|
||||
case FormatEntity::Entry::Type::FunctionScope: {
|
||||
std::optional<llvm::StringRef> scope = GetDemangledScope(sc);
|
||||
if (!scope)
|
||||
auto scope_or_err = GetDemangledScope(sc);
|
||||
if (!scope_or_err) {
|
||||
LLDB_LOG_ERROR(
|
||||
GetLog(LLDBLog::Language), scope_or_err.takeError(),
|
||||
"Failed to handle ${{function.scope}} frame-format variable: {0}");
|
||||
return false;
|
||||
}
|
||||
|
||||
s << *scope;
|
||||
s << *scope_or_err;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
case FormatEntity::Entry::Type::FunctionBasename: {
|
||||
std::optional<llvm::StringRef> name = GetDemangledBasename(sc);
|
||||
if (!name)
|
||||
auto name_or_err = GetDemangledBasename(sc);
|
||||
if (!name_or_err) {
|
||||
LLDB_LOG_ERROR(
|
||||
GetLog(LLDBLog::Language), name_or_err.takeError(),
|
||||
"Failed to handle ${{function.basename}} frame-format variable: {0}");
|
||||
return false;
|
||||
}
|
||||
|
||||
s << *name;
|
||||
s << *name_or_err;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
case FormatEntity::Entry::Type::FunctionTemplateArguments: {
|
||||
std::optional<llvm::StringRef> template_args =
|
||||
GetDemangledTemplateArguments(sc);
|
||||
if (!template_args)
|
||||
auto template_args_or_err = GetDemangledTemplateArguments(sc);
|
||||
if (!template_args_or_err) {
|
||||
LLDB_LOG_ERROR(GetLog(LLDBLog::Language),
|
||||
template_args_or_err.takeError(),
|
||||
"Failed to handle ${{function.template-arguments}} "
|
||||
"frame-format variable: {0}");
|
||||
return false;
|
||||
}
|
||||
|
||||
s << *template_args;
|
||||
s << *template_args_or_err;
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -2008,38 +1979,54 @@ bool CPlusPlusLanguage::HandleFrameFormatVariable(
|
||||
return true;
|
||||
}
|
||||
case FormatEntity::Entry::Type::FunctionReturnRight: {
|
||||
std::optional<llvm::StringRef> return_rhs = GetDemangledReturnTypeRHS(sc);
|
||||
if (!return_rhs)
|
||||
auto return_rhs_or_err = GetDemangledReturnTypeRHS(sc);
|
||||
if (!return_rhs_or_err) {
|
||||
LLDB_LOG_ERROR(GetLog(LLDBLog::Language), return_rhs_or_err.takeError(),
|
||||
"Failed to handle ${{function.return-right}} frame-format "
|
||||
"variable: {0}");
|
||||
return false;
|
||||
}
|
||||
|
||||
s << *return_rhs;
|
||||
s << *return_rhs_or_err;
|
||||
|
||||
return true;
|
||||
}
|
||||
case FormatEntity::Entry::Type::FunctionReturnLeft: {
|
||||
std::optional<llvm::StringRef> return_lhs = GetDemangledReturnTypeLHS(sc);
|
||||
if (!return_lhs)
|
||||
auto return_lhs_or_err = GetDemangledReturnTypeLHS(sc);
|
||||
if (!return_lhs_or_err) {
|
||||
LLDB_LOG_ERROR(GetLog(LLDBLog::Language), return_lhs_or_err.takeError(),
|
||||
"Failed to handle ${{function.return-left}} frame-format "
|
||||
"variable: {0}");
|
||||
return false;
|
||||
}
|
||||
|
||||
s << *return_lhs;
|
||||
s << *return_lhs_or_err;
|
||||
|
||||
return true;
|
||||
}
|
||||
case FormatEntity::Entry::Type::FunctionQualifiers: {
|
||||
std::optional<llvm::StringRef> quals = GetDemangledFunctionQualifiers(sc);
|
||||
if (!quals)
|
||||
auto quals_or_err = GetDemangledFunctionQualifiers(sc);
|
||||
if (!quals_or_err) {
|
||||
LLDB_LOG_ERROR(GetLog(LLDBLog::Language), quals_or_err.takeError(),
|
||||
"Failed to handle ${{function.qualifiers}} frame-format "
|
||||
"variable: {0}");
|
||||
return false;
|
||||
}
|
||||
|
||||
s << *quals;
|
||||
s << *quals_or_err;
|
||||
|
||||
return true;
|
||||
}
|
||||
case FormatEntity::Entry::Type::FunctionSuffix: {
|
||||
std::optional<llvm::StringRef> suffix = GetDemangledFunctionSuffix(sc);
|
||||
if (!suffix)
|
||||
auto suffix_or_err = GetDemangledFunctionSuffix(sc);
|
||||
if (!suffix_or_err) {
|
||||
LLDB_LOG_ERROR(
|
||||
GetLog(LLDBLog::Language), suffix_or_err.takeError(),
|
||||
"Failed to handle ${{function.suffix}} frame-format variable: {0}");
|
||||
return false;
|
||||
}
|
||||
|
||||
s << *suffix;
|
||||
s << *suffix_or_err;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -648,43 +648,43 @@ struct DemangledNameInfoTestCase {
|
||||
DemangledNameInfoTestCase g_demangled_name_info_test_cases[] = {
|
||||
// clang-format off
|
||||
{
|
||||
{ /*.BasenameRange=*/{0, 10}, /*.ScopeRange=*/{0, 0}, /*.ArgumentsRange=*/{0, 0},
|
||||
/*.QualifiersRange=*/{0, 0}, /*.PrefixRange=*/{0, 0}, /*.SuffixRange=*/{0, 0}
|
||||
{ /*.BasenameRange=*/{0, 10}, /*.ScopeRange=*/{1, 0}, /*.ArgumentsRange=*/{1, 0},
|
||||
/*.QualifiersRange=*/{1, 0}, /*.PrefixRange=*/{1, 0}, /*.SuffixRange=*/{1, 0}
|
||||
},
|
||||
/*valid_basename=*/true, /*valid_scope=*/false, /*valid_arguments=*/false,
|
||||
/*valid_qualifiers=*/false, /*valid_prefix=*/false, /*valid_suffix=*/false,
|
||||
},
|
||||
{
|
||||
{ /*.BasenameRange=*/{0, 0}, /*.ScopeRange=*/{0, 10}, /*.ArgumentsRange=*/{0, 0},
|
||||
/*.QualifiersRange=*/{0, 0}, /*.PrefixRange=*/{0, 0}, /*.SuffixRange=*/{0, 0}
|
||||
{ /*.BasenameRange=*/{1, 0}, /*.ScopeRange=*/{0, 10}, /*.ArgumentsRange=*/{1, 0},
|
||||
/*.QualifiersRange=*/{1, 0}, /*.PrefixRange=*/{1, 0}, /*.SuffixRange=*/{1, 0}
|
||||
},
|
||||
/*valid_basename=*/false, /*valid_scope=*/true, /*valid_arguments=*/false,
|
||||
/*valid_qualifiers=*/false, /*valid_prefix=*/false, /*valid_suffix=*/false,
|
||||
},
|
||||
{
|
||||
{ /*.BasenameRange=*/{0, 0}, /*.ScopeRange=*/{0, 0}, /*.ArgumentsRange=*/{0, 10},
|
||||
/*.QualifiersRange=*/{0, 0}, /*.PrefixRange=*/{0, 0}, /*.SuffixRange=*/{0, 0}
|
||||
{ /*.BasenameRange=*/{1, 0}, /*.ScopeRange=*/{1, 0}, /*.ArgumentsRange=*/{0, 10},
|
||||
/*.QualifiersRange=*/{1, 0}, /*.PrefixRange=*/{1, 0}, /*.SuffixRange=*/{1, 0}
|
||||
},
|
||||
/*valid_basename=*/false, /*valid_scope=*/false, /*valid_arguments=*/true,
|
||||
/*valid_qualifiers=*/false, /*valid_prefix=*/false, /*valid_suffix=*/false,
|
||||
},
|
||||
{
|
||||
{ /*.BasenameRange=*/{0, 0}, /*.ScopeRange=*/{0, 0}, /*.ArgumentsRange=*/{0, 0},
|
||||
/*.QualifiersRange=*/{0, 10}, /*.PrefixRange=*/{0, 0}, /*.SuffixRange=*/{0, 0}
|
||||
{ /*.BasenameRange=*/{1, 0}, /*.ScopeRange=*/{1, 0}, /*.ArgumentsRange=*/{1, 0},
|
||||
/*.QualifiersRange=*/{0, 10}, /*.PrefixRange=*/{1, 0}, /*.SuffixRange=*/{1, 0}
|
||||
},
|
||||
/*valid_basename=*/false, /*valid_scope=*/false, /*valid_arguments=*/false,
|
||||
/*valid_qualifiers=*/true, /*valid_prefix=*/false, /*valid_suffix=*/false,
|
||||
},
|
||||
{
|
||||
{ /*.BasenameRange=*/{0, 0}, /*.ScopeRange=*/{0, 0}, /*.ArgumentsRange=*/{0, 0},
|
||||
/*.QualifiersRange=*/{0, 0}, /*.PrefixRange=*/{0, 10}, /*.SuffixRange=*/{0, 0}
|
||||
{ /*.BasenameRange=*/{1, 0}, /*.ScopeRange=*/{1, 0}, /*.ArgumentsRange=*/{1, 0},
|
||||
/*.QualifiersRange=*/{1, 0}, /*.PrefixRange=*/{0, 10}, /*.SuffixRange=*/{1, 0}
|
||||
},
|
||||
/*valid_basename=*/false, /*valid_scope=*/false, /*valid_arguments=*/false,
|
||||
/*valid_qualifiers=*/false, /*valid_prefix=*/true, /*valid_suffix=*/false,
|
||||
},
|
||||
{
|
||||
{ /*.BasenameRange=*/{0, 0}, /*.ScopeRange=*/{0, 0}, /*.ArgumentsRange=*/{0, 0},
|
||||
/*.QualifiersRange=*/{0, 0}, /*.PrefixRange=*/{0, 0}, /*.SuffixRange=*/{0, 10}
|
||||
{ /*.BasenameRange=*/{1, 0}, /*.ScopeRange=*/{1, 0}, /*.ArgumentsRange=*/{1, 0},
|
||||
/*.QualifiersRange=*/{1, 0}, /*.PrefixRange=*/{1, 0}, /*.SuffixRange=*/{0, 10}
|
||||
},
|
||||
/*valid_basename=*/false, /*valid_scope=*/false, /*valid_arguments=*/false,
|
||||
/*valid_qualifiers=*/false, /*valid_prefix=*/false, /*valid_suffix=*/true,
|
||||
|
||||
Reference in New Issue
Block a user