Fix is_public and is_class_member for scoped/unscoped enum (#194)

* Add bubble up for unscoped enum in membership check

Check membership for public check access

Signed-off-by: zebullax <zebullax@gmail.com>

* Fix golden copy for generated headers

Signed-off-by: zebullax <zebullax@gmail.com>

* Skip validation of reflection unittest that introduce non ascii character

Signed-off-by: zebullax <zebullax@gmail.com>

* Check class membership for is_private/protected/public

Signed-off-by: zebullax <zebullax@gmail.com>

---------

Signed-off-by: zebullax <zebullax@gmail.com>
This commit is contained in:
zebullax
2025-10-22 17:46:23 +09:00
committed by GitHub
parent 63a00eeeed
commit 9171cf41ef
4 changed files with 81 additions and 12 deletions

View File

@@ -3324,31 +3324,62 @@ bool is_ACCESS(APValue &Result, ASTContext &C, MetaActions &Meta,
llvm_unreachable("invalid reflection type");
}
template <AccessSpecifier AS>
static inline
bool is_ClassMember_ACCESS(APValue &Result, ASTContext &C, MetaActions &Meta,
EvalFn Evaluator, DiagFn Diagnoser, bool AllowInjection,
QualType ResultTy, SourceRange Range, ArrayRef<Expr *> Args,
Decl *ContainingDecl) {
[[maybe_unused]] bool scratch
= is_class_member(Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
if (const bool isClassMember = Result.getInt().getBoolValue();isClassMember) {
return is_ACCESS<AS>(Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
}
// fallthrough: base-class relationship
scratch = is_base(Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
if (const bool isBaseClass = Result.getInt().getBoolValue();isBaseClass) {
return is_ACCESS<AS>(Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
}
return false;
}
bool is_public(APValue &Result, ASTContext &C, MetaActions &Meta,
EvalFn Evaluator, DiagFn Diagnoser, bool AllowInjection,
QualType ResultTy, SourceRange Range, ArrayRef<Expr *> Args,
Decl *ContainingDecl) {
return is_ACCESS<AS_public>(Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
return is_ClassMember_ACCESS<AS_public>(
Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
}
bool is_protected(APValue &Result, ASTContext &C, MetaActions &Meta,
EvalFn Evaluator, DiagFn Diagnoser, bool AllowInjection,
QualType ResultTy, SourceRange Range, ArrayRef<Expr *> Args,
Decl *ContainingDecl) {
return is_ACCESS<AS_protected>(Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
return is_ClassMember_ACCESS<AS_protected>(
Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
}
bool is_private(APValue &Result, ASTContext &C, MetaActions &Meta,
EvalFn Evaluator, DiagFn Diagnoser, bool AllowInjection,
QualType ResultTy, SourceRange Range, ArrayRef<Expr *> Args,
Decl *ContainingDecl) {
return is_ACCESS<AS_private>(Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
return is_ClassMember_ACCESS<AS_private>(
Result, C, Meta, Evaluator, Diagnoser,
AllowInjection, ResultTy, Range, Args,
ContainingDecl);
}
bool is_virtual(APValue &Result, ASTContext &C, MetaActions &Meta,
@@ -3890,7 +3921,6 @@ bool is_class_member(APValue &Result, ASTContext &C, MetaActions &Meta,
ArrayRef<Expr *> Args, Decl *ContainingDecl) {
assert(Args[0]->getType()->isReflectionType());
assert(ResultTy == C.BoolTy);
APValue Scratch;
bool result = false;
@@ -3898,8 +3928,15 @@ bool is_class_member(APValue &Result, ASTContext &C, MetaActions &Meta,
if (!parent_of(Scratch, C, Meta, Evaluator, SwallowDiags, AllowInjection,
C.MetaInfoTy, Range, Args, ContainingDecl)) {
assert(Scratch.isReflection());
result = Scratch.isReflectedType() &&
Scratch.getReflectedType()->isRecordType();
// For unscoped enumerators, parent_of will return its enumeration type
// We need now to lookup context on that type
if (Scratch.isReflectedType() && Scratch.getReflectedType()->isUnscopedEnumerationType()) {
Decl *D = findTypeDecl(Scratch.getReflectedType());
result = D && D->getDeclContext() && D->getDeclContext()->isRecord();
} else {
result = Scratch.isReflectedType() &&
Scratch.getReflectedType()->isRecordType();
}
}
return SetAndSucceed(Result, makeBool(C, result));
}