1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133
|
//===--- State.h - State chain for the VM and AST Walker --------*- C++ -*-===//
//
// 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
//
//===----------------------------------------------------------------------===//
//
// Defines the base class of the interpreter and evaluator state.
//
//===----------------------------------------------------------------------===//
#ifndef LLVM_CLANG_AST_INTERP_STATE_H
#define LLVM_CLANG_AST_INTERP_STATE_H
#include "clang/AST/ASTDiagnostic.h"
#include "clang/AST/Expr.h"
#include "clang/AST/OptionalDiagnostic.h"
namespace clang {
/// Kinds of access we can perform on an object, for diagnostics. Note that
/// we consider a member function call to be a kind of access, even though
/// it is not formally an access of the object, because it has (largely) the
/// same set of semantic restrictions.
enum AccessKinds {
AK_Read,
AK_ReadObjectRepresentation,
AK_Assign,
AK_Increment,
AK_Decrement,
AK_MemberCall,
AK_DynamicCast,
AK_TypeId,
AK_Construct,
AK_Destroy,
};
// The order of this enum is important for diagnostics.
enum CheckSubobjectKind {
CSK_Base,
CSK_Derived,
CSK_Field,
CSK_ArrayToPointer,
CSK_ArrayIndex,
CSK_Real,
CSK_Imag
};
namespace interp {
class Frame;
class SourceInfo;
/// Interface for the VM to interact with the AST walker's context.
class State {
public:
virtual ~State();
virtual bool checkingForUndefinedBehavior() const = 0;
virtual bool checkingPotentialConstantExpression() const = 0;
virtual bool noteUndefinedBehavior() = 0;
virtual bool keepEvaluatingAfterFailure() const = 0;
virtual Frame *getCurrentFrame() = 0;
virtual const Frame *getBottomFrame() const = 0;
virtual bool hasActiveDiagnostic() = 0;
virtual void setActiveDiagnostic(bool Flag) = 0;
virtual void setFoldFailureDiagnostic(bool Flag) = 0;
virtual Expr::EvalStatus &getEvalStatus() const = 0;
virtual ASTContext &getCtx() const = 0;
virtual bool hasPriorDiagnostic() = 0;
virtual unsigned getCallStackDepth() = 0;
public:
// Diagnose that the evaluation could not be folded (FF => FoldFailure)
OptionalDiagnostic
FFDiag(SourceLocation Loc,
diag::kind DiagId = diag::note_invalid_subexpr_in_const_expr,
unsigned ExtraNotes = 0);
OptionalDiagnostic
FFDiag(const Expr *E,
diag::kind DiagId = diag::note_invalid_subexpr_in_const_expr,
unsigned ExtraNotes = 0);
OptionalDiagnostic
FFDiag(const SourceInfo &SI,
diag::kind DiagId = diag::note_invalid_subexpr_in_const_expr,
unsigned ExtraNotes = 0);
/// Diagnose that the evaluation does not produce a C++11 core constant
/// expression.
///
/// FIXME: Stop evaluating if we're in EM_ConstantExpression or
/// EM_PotentialConstantExpression mode and we produce one of these.
OptionalDiagnostic
CCEDiag(SourceLocation Loc,
diag::kind DiagId = diag::note_invalid_subexpr_in_const_expr,
unsigned ExtraNotes = 0);
OptionalDiagnostic
CCEDiag(const Expr *E,
diag::kind DiagId = diag::note_invalid_subexpr_in_const_expr,
unsigned ExtraNotes = 0);
OptionalDiagnostic
CCEDiag(const SourceInfo &SI,
diag::kind DiagId = diag::note_invalid_subexpr_in_const_expr,
unsigned ExtraNotes = 0);
/// Add a note to a prior diagnostic.
OptionalDiagnostic Note(SourceLocation Loc, diag::kind DiagId);
/// Add a stack of notes to a prior diagnostic.
void addNotes(ArrayRef<PartialDiagnosticAt> Diags);
/// Directly reports a diagnostic message.
DiagnosticBuilder report(SourceLocation Loc, diag::kind DiagId);
const LangOptions &getLangOpts() const;
private:
void addCallStack(unsigned Limit);
PartialDiagnostic &addDiag(SourceLocation Loc, diag::kind DiagId);
OptionalDiagnostic diag(SourceLocation Loc, diag::kind DiagId,
unsigned ExtraNotes, bool IsCCEDiag);
};
} // namespace interp
} // namespace clang
#endif
|