diff options
Diffstat (limited to 'clang/lib/AST/ByteCode')
| -rw-r--r-- | clang/lib/AST/ByteCode/Compiler.cpp | 17 | ||||
| -rw-r--r-- | clang/lib/AST/ByteCode/Interp.h | 25 | ||||
| -rw-r--r-- | clang/lib/AST/ByteCode/InterpBuiltin.cpp | 12 | ||||
| -rw-r--r-- | clang/lib/AST/ByteCode/Opcodes.td | 2 | ||||
| -rw-r--r-- | clang/lib/AST/ByteCode/Pointer.cpp | 2 |
5 files changed, 45 insertions, 13 deletions
diff --git a/clang/lib/AST/ByteCode/Compiler.cpp b/clang/lib/AST/ByteCode/Compiler.cpp index 672fa7fc25d6..b960954d4754 100644 --- a/clang/lib/AST/ByteCode/Compiler.cpp +++ b/clang/lib/AST/ByteCode/Compiler.cpp @@ -5738,9 +5738,17 @@ bool Compiler<Emitter>::VisitUnaryOperator(const UnaryOperator *E) { // We should already have a pointer when we get here. return this->delegate(SubExpr); case UO_Deref: // *x - if (DiscardResult) + if (DiscardResult) { + // assert(false); return this->discard(SubExpr); - return this->visit(SubExpr); + } + + if (!this->visit(SubExpr)) + return false; + if (classifyPrim(SubExpr) == PT_Ptr) + return this->emitNarrowPtr(E); + return true; + case UO_Not: // ~x if (!T) return this->emitError(E); @@ -6089,7 +6097,8 @@ bool Compiler<Emitter>::visitDeclRef(const ValueDecl *D, const Expr *E) { if (VD->evaluateValue()) return revisit(VD); - return this->emitInvalidDeclRef(cast<DeclRefExpr>(E), E); + return this->emitInvalidDeclRef(cast<DeclRefExpr>(E), + /*InitializerFailed=*/true, E); } } } else { @@ -6115,7 +6124,7 @@ bool Compiler<Emitter>::visitDeclRef(const ValueDecl *D, const Expr *E) { } if (const auto *DRE = dyn_cast<DeclRefExpr>(E)) - return this->emitInvalidDeclRef(DRE, E); + return this->emitInvalidDeclRef(DRE, /*InitializerFailed=*/false, E); return false; } diff --git a/clang/lib/AST/ByteCode/Interp.h b/clang/lib/AST/ByteCode/Interp.h index aafc848a9c53..c95b18ef72c9 100644 --- a/clang/lib/AST/ByteCode/Interp.h +++ b/clang/lib/AST/ByteCode/Interp.h @@ -1944,14 +1944,14 @@ inline bool CastMemberPtrPtr(InterpState &S, CodePtr OpPC) { template <class T, ArithOp Op> bool OffsetHelper(InterpState &S, CodePtr OpPC, const T &Offset, - const Pointer &Ptr) { + const Pointer &Ptr, bool IsPointerArith = false) { // A zero offset does not change the pointer. if (Offset.isZero()) { S.Stk.push<Pointer>(Ptr); return true; } - if (!CheckNull(S, OpPC, Ptr, CSK_ArrayIndex)) { + if (IsPointerArith && !CheckNull(S, OpPC, Ptr, CSK_ArrayIndex)) { // The CheckNull will have emitted a note already, but we only // abort in C++, since this is fine in C. if (S.getLangOpts().CPlusPlus) @@ -2063,14 +2063,16 @@ bool AddOffset(InterpState &S, CodePtr OpPC) { Pointer Ptr = S.Stk.pop<Pointer>(); if (Ptr.isBlockPointer()) Ptr = Ptr.expand(); - return OffsetHelper<T, ArithOp::Add>(S, OpPC, Offset, Ptr); + return OffsetHelper<T, ArithOp::Add>(S, OpPC, Offset, Ptr, + /*IsPointerArith=*/true); } template <PrimType Name, class T = typename PrimConv<Name>::T> bool SubOffset(InterpState &S, CodePtr OpPC) { const T &Offset = S.Stk.pop<T>(); const Pointer &Ptr = S.Stk.pop<Pointer>(); - return OffsetHelper<T, ArithOp::Sub>(S, OpPC, Offset, Ptr); + return OffsetHelper<T, ArithOp::Sub>(S, OpPC, Offset, Ptr, + /*IsPointerArith=*/true); } template <ArithOp Op> @@ -2090,7 +2092,7 @@ static inline bool IncDecPtrHelper(InterpState &S, CodePtr OpPC, // Now the current Ptr again and a constant 1. OneT One = OneT::from(1); - if (!OffsetHelper<OneT, Op>(S, OpPC, One, P)) + if (!OffsetHelper<OneT, Op>(S, OpPC, One, P, /*IsPointerArith=*/true)) return false; // Store the new value. @@ -2816,9 +2818,18 @@ inline bool InvalidCast(InterpState &S, CodePtr OpPC, CastKind Kind, return false; } -inline bool InvalidDeclRef(InterpState &S, CodePtr OpPC, - const DeclRefExpr *DR) { +inline bool InvalidDeclRef(InterpState &S, CodePtr OpPC, const DeclRefExpr *DR, + bool InitializerFailed) { assert(DR); + + if (InitializerFailed) { + const SourceInfo &Loc = S.Current->getSource(OpPC); + const auto *VD = cast<VarDecl>(DR->getDecl()); + S.FFDiag(Loc, diag::note_constexpr_var_init_non_constant, 1) << VD; + S.Note(VD->getLocation(), diag::note_declared_at); + return false; + } + return CheckDeclRef(S, OpPC, DR); } diff --git a/clang/lib/AST/ByteCode/InterpBuiltin.cpp b/clang/lib/AST/ByteCode/InterpBuiltin.cpp index d4a8e6c2035e..10e33c14f4b4 100644 --- a/clang/lib/AST/ByteCode/InterpBuiltin.cpp +++ b/clang/lib/AST/ByteCode/InterpBuiltin.cpp @@ -1253,6 +1253,10 @@ static bool interp__builtin_ia32_bextr(InterpState &S, CodePtr OpPC, const InterpFrame *Frame, const Function *Func, const CallExpr *Call) { + if (!Call->getArg(0)->getType()->isIntegerType() || + !Call->getArg(1)->getType()->isIntegerType()) + return false; + PrimType ValT = *S.Ctx.classify(Call->getArg(0)); PrimType IndexT = *S.Ctx.classify(Call->getArg(1)); APSInt Val = peekToAPSInt(S.Stk, ValT, @@ -1331,6 +1335,10 @@ static bool interp__builtin_ia32_pdep(InterpState &S, CodePtr OpPC, const InterpFrame *Frame, const Function *Func, const CallExpr *Call) { + if (!Call->getArg(0)->getType()->isIntegerType() || + !Call->getArg(1)->getType()->isIntegerType()) + return false; + PrimType ValT = *S.Ctx.classify(Call->getArg(0)); PrimType MaskT = *S.Ctx.classify(Call->getArg(1)); @@ -1352,6 +1360,10 @@ static bool interp__builtin_ia32_pext(InterpState &S, CodePtr OpPC, const InterpFrame *Frame, const Function *Func, const CallExpr *Call) { + if (!Call->getArg(0)->getType()->isIntegerType() || + !Call->getArg(1)->getType()->isIntegerType()) + return false; + PrimType ValT = *S.Ctx.classify(Call->getArg(0)); PrimType MaskT = *S.Ctx.classify(Call->getArg(1)); diff --git a/clang/lib/AST/ByteCode/Opcodes.td b/clang/lib/AST/ByteCode/Opcodes.td index a1970f25ca97..9136e6b51660 100644 --- a/clang/lib/AST/ByteCode/Opcodes.td +++ b/clang/lib/AST/ByteCode/Opcodes.td @@ -769,7 +769,7 @@ def InvalidCast : Opcode { } def InvalidDeclRef : Opcode { - let Args = [ArgDeclRef]; + let Args = [ArgDeclRef, ArgBool]; } def SizelessVectorElementSize : Opcode; diff --git a/clang/lib/AST/ByteCode/Pointer.cpp b/clang/lib/AST/ByteCode/Pointer.cpp index 75b00dcb2ab2..c9de039c195d 100644 --- a/clang/lib/AST/ByteCode/Pointer.cpp +++ b/clang/lib/AST/ByteCode/Pointer.cpp @@ -635,7 +635,7 @@ std::optional<APValue> Pointer::toRValue(const Context &Ctx, // Return the composite type. APValue Result; - if (!Composite(getType(), *this, Result)) + if (!Composite(ResultType, *this, Result)) return std::nullopt; return Result; } |
