diff options
author | Timm Baeder <tbaeder@redhat.com> | 2025-04-24 17:04:36 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2025-04-24 17:04:36 +0200 |
commit | 9ae7aa79b1e151c3af12b9ffec0e2fdeacde5cc9 (patch) | |
tree | d75204057903bf68771d58c2a120571df1d71bf6 /clang/lib/AST/ByteCode/Pointer.cpp | |
parent | d859cb68836191cfa469d0c951134b53ee31298e (diff) | |
download | llvm-9ae7aa79b1e151c3af12b9ffec0e2fdeacde5cc9.zip llvm-9ae7aa79b1e151c3af12b9ffec0e2fdeacde5cc9.tar.gz llvm-9ae7aa79b1e151c3af12b9ffec0e2fdeacde5cc9.tar.bz2 |
[clang][bytecode] Diagnose comparing pointers to fields... (#137159)
... with different access specifiers.
Diffstat (limited to 'clang/lib/AST/ByteCode/Pointer.cpp')
-rw-r--r-- | clang/lib/AST/ByteCode/Pointer.cpp | 42 |
1 files changed, 42 insertions, 0 deletions
diff --git a/clang/lib/AST/ByteCode/Pointer.cpp b/clang/lib/AST/ByteCode/Pointer.cpp index 059503c..6c2566b 100644 --- a/clang/lib/AST/ByteCode/Pointer.cpp +++ b/clang/lib/AST/ByteCode/Pointer.cpp @@ -571,6 +571,48 @@ bool Pointer::pointsToLiteral() const { return E && !isa<MaterializeTemporaryExpr, StringLiteral>(E); } +std::optional<std::pair<Pointer, Pointer>> +Pointer::computeSplitPoint(const Pointer &A, const Pointer &B) { + if (!A.isBlockPointer() || !B.isBlockPointer()) + return std::nullopt; + + if (A.asBlockPointer().Pointee != B.asBlockPointer().Pointee) + return std::nullopt; + if (A.isRoot() && B.isRoot()) + return std::nullopt; + + if (A == B) + return std::make_pair(A, B); + + auto getBase = [](const Pointer &P) -> Pointer { + if (P.isArrayElement()) + return P.expand().getArray(); + return P.getBase(); + }; + + Pointer IterA = A; + Pointer IterB = B; + Pointer CurA = IterA; + Pointer CurB = IterB; + for (;;) { + if (IterA.asBlockPointer().Base > IterB.asBlockPointer().Base) { + CurA = IterA; + IterA = getBase(IterA); + } else { + CurB = IterB; + IterB = getBase(IterB); + } + + if (IterA == IterB) + return std::make_pair(CurA, CurB); + + if (IterA.isRoot() && IterB.isRoot()) + return std::nullopt; + } + + llvm_unreachable("The loop above should've returned."); +} + std::optional<APValue> Pointer::toRValue(const Context &Ctx, QualType ResultType) const { const ASTContext &ASTCtx = Ctx.getASTContext(); |