aboutsummaryrefslogtreecommitdiffstats
path: root/contrib/libs/clang16/include/clang/Analysis/Analyses/Consumed.h
diff options
context:
space:
mode:
authorthegeorg <thegeorg@yandex-team.com>2024-03-13 13:58:24 +0300
committerthegeorg <thegeorg@yandex-team.com>2024-03-13 14:11:53 +0300
commit11a895b7e15d1c5a1f52706396b82e3f9db953cb (patch)
treefabc6d883b0f946151f61ae7865cee9f529a1fdd /contrib/libs/clang16/include/clang/Analysis/Analyses/Consumed.h
parent9685917341315774aad5733b1793b1e533a88bbb (diff)
downloadydb-11a895b7e15d1c5a1f52706396b82e3f9db953cb.tar.gz
Export clang-format16 via ydblib project
6e6be3a95868fde888d801b7590af4044049563f
Diffstat (limited to 'contrib/libs/clang16/include/clang/Analysis/Analyses/Consumed.h')
-rw-r--r--contrib/libs/clang16/include/clang/Analysis/Analyses/Consumed.h282
1 files changed, 282 insertions, 0 deletions
diff --git a/contrib/libs/clang16/include/clang/Analysis/Analyses/Consumed.h b/contrib/libs/clang16/include/clang/Analysis/Analyses/Consumed.h
new file mode 100644
index 0000000000..e45a3f75e0
--- /dev/null
+++ b/contrib/libs/clang16/include/clang/Analysis/Analyses/Consumed.h
@@ -0,0 +1,282 @@
+#pragma once
+
+#ifdef __GNUC__
+#pragma GCC diagnostic push
+#pragma GCC diagnostic ignored "-Wunused-parameter"
+#endif
+
+//===- Consumed.h -----------------------------------------------*- 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
+//
+//===----------------------------------------------------------------------===//
+//
+// A intra-procedural analysis for checking consumed properties. This is based,
+// in part, on research on linear types.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_ANALYSIS_ANALYSES_CONSUMED_H
+#define LLVM_CLANG_ANALYSIS_ANALYSES_CONSUMED_H
+
+#include "clang/Analysis/Analyses/PostOrderCFGView.h"
+#include "clang/Analysis/CFG.h"
+#include "clang/Basic/LLVM.h"
+#include "clang/Basic/PartialDiagnostic.h"
+#include "clang/Basic/SourceLocation.h"
+#include "llvm/ADT/DenseMap.h"
+#include "llvm/ADT/SmallVector.h"
+#include "llvm/ADT/StringRef.h"
+#include <list>
+#include <memory>
+#include <utility>
+#include <vector>
+
+namespace clang {
+
+class AnalysisDeclContext;
+class CXXBindTemporaryExpr;
+class FunctionDecl;
+class PostOrderCFGView;
+class Stmt;
+class VarDecl;
+
+namespace consumed {
+
+ class ConsumedStmtVisitor;
+
+ enum ConsumedState {
+ // No state information for the given variable.
+ CS_None,
+
+ CS_Unknown,
+ CS_Unconsumed,
+ CS_Consumed
+ };
+
+ using OptionalNotes = SmallVector<PartialDiagnosticAt, 1>;
+ using DelayedDiag = std::pair<PartialDiagnosticAt, OptionalNotes>;
+ using DiagList = std::list<DelayedDiag>;
+
+ class ConsumedWarningsHandlerBase {
+ public:
+ virtual ~ConsumedWarningsHandlerBase();
+
+ /// Emit the warnings and notes left by the analysis.
+ virtual void emitDiagnostics() {}
+
+ /// Warn that a variable's state doesn't match at the entry and exit
+ /// of a loop.
+ ///
+ /// \param Loc -- The location of the end of the loop.
+ ///
+ /// \param VariableName -- The name of the variable that has a mismatched
+ /// state.
+ virtual void warnLoopStateMismatch(SourceLocation Loc,
+ StringRef VariableName) {}
+
+ /// Warn about parameter typestate mismatches upon return.
+ ///
+ /// \param Loc -- The SourceLocation of the return statement.
+ ///
+ /// \param ExpectedState -- The state the return value was expected to be
+ /// in.
+ ///
+ /// \param ObservedState -- The state the return value was observed to be
+ /// in.
+ virtual void warnParamReturnTypestateMismatch(SourceLocation Loc,
+ StringRef VariableName,
+ StringRef ExpectedState,
+ StringRef ObservedState) {}
+
+ // FIXME: Add documentation.
+ virtual void warnParamTypestateMismatch(SourceLocation LOC,
+ StringRef ExpectedState,
+ StringRef ObservedState) {}
+
+ // FIXME: This can be removed when the attr propagation fix for templated
+ // classes lands.
+ /// Warn about return typestates set for unconsumable types.
+ ///
+ /// \param Loc -- The location of the attributes.
+ ///
+ /// \param TypeName -- The name of the unconsumable type.
+ virtual void warnReturnTypestateForUnconsumableType(SourceLocation Loc,
+ StringRef TypeName) {}
+
+ /// Warn about return typestate mismatches.
+ ///
+ /// \param Loc -- The SourceLocation of the return statement.
+ ///
+ /// \param ExpectedState -- The state the return value was expected to be
+ /// in.
+ ///
+ /// \param ObservedState -- The state the return value was observed to be
+ /// in.
+ virtual void warnReturnTypestateMismatch(SourceLocation Loc,
+ StringRef ExpectedState,
+ StringRef ObservedState) {}
+
+ /// Warn about use-while-consumed errors.
+ /// \param MethodName -- The name of the method that was incorrectly
+ /// invoked.
+ ///
+ /// \param State -- The state the object was used in.
+ ///
+ /// \param Loc -- The SourceLocation of the method invocation.
+ virtual void warnUseOfTempInInvalidState(StringRef MethodName,
+ StringRef State,
+ SourceLocation Loc) {}
+
+ /// Warn about use-while-consumed errors.
+ /// \param MethodName -- The name of the method that was incorrectly
+ /// invoked.
+ ///
+ /// \param State -- The state the object was used in.
+ ///
+ /// \param VariableName -- The name of the variable that holds the unique
+ /// value.
+ ///
+ /// \param Loc -- The SourceLocation of the method invocation.
+ virtual void warnUseInInvalidState(StringRef MethodName,
+ StringRef VariableName,
+ StringRef State,
+ SourceLocation Loc) {}
+ };
+
+ class ConsumedStateMap {
+ using VarMapType = llvm::DenseMap<const VarDecl *, ConsumedState>;
+ using TmpMapType =
+ llvm::DenseMap<const CXXBindTemporaryExpr *, ConsumedState>;
+
+ protected:
+ bool Reachable = true;
+ const Stmt *From = nullptr;
+ VarMapType VarMap;
+ TmpMapType TmpMap;
+
+ public:
+ ConsumedStateMap() = default;
+ ConsumedStateMap(const ConsumedStateMap &Other)
+ : Reachable(Other.Reachable), From(Other.From), VarMap(Other.VarMap) {}
+
+ /// Warn if any of the parameters being tracked are not in the state
+ /// they were declared to be in upon return from a function.
+ void checkParamsForReturnTypestate(SourceLocation BlameLoc,
+ ConsumedWarningsHandlerBase &WarningsHandler) const;
+
+ /// Clear the TmpMap.
+ void clearTemporaries();
+
+ /// Get the consumed state of a given variable.
+ ConsumedState getState(const VarDecl *Var) const;
+
+ /// Get the consumed state of a given temporary value.
+ ConsumedState getState(const CXXBindTemporaryExpr *Tmp) const;
+
+ /// Merge this state map with another map.
+ void intersect(const ConsumedStateMap &Other);
+
+ void intersectAtLoopHead(const CFGBlock *LoopHead, const CFGBlock *LoopBack,
+ const ConsumedStateMap *LoopBackStates,
+ ConsumedWarningsHandlerBase &WarningsHandler);
+
+ /// Return true if this block is reachable.
+ bool isReachable() const { return Reachable; }
+
+ /// Mark the block as unreachable.
+ void markUnreachable();
+
+ /// Set the source for a decision about the branching of states.
+ /// \param Source -- The statement that was the origin of a branching
+ /// decision.
+ void setSource(const Stmt *Source) { this->From = Source; }
+
+ /// Set the consumed state of a given variable.
+ void setState(const VarDecl *Var, ConsumedState State);
+
+ /// Set the consumed state of a given temporary value.
+ void setState(const CXXBindTemporaryExpr *Tmp, ConsumedState State);
+
+ /// Remove the temporary value from our state map.
+ void remove(const CXXBindTemporaryExpr *Tmp);
+
+ /// Tests to see if there is a mismatch in the states stored in two
+ /// maps.
+ ///
+ /// \param Other -- The second map to compare against.
+ bool operator!=(const ConsumedStateMap *Other) const;
+ };
+
+ class ConsumedBlockInfo {
+ std::vector<std::unique_ptr<ConsumedStateMap>> StateMapsArray;
+ std::vector<unsigned int> VisitOrder;
+
+ public:
+ ConsumedBlockInfo() = default;
+
+ ConsumedBlockInfo(unsigned int NumBlocks, PostOrderCFGView *SortedGraph)
+ : StateMapsArray(NumBlocks), VisitOrder(NumBlocks, 0) {
+ unsigned int VisitOrderCounter = 0;
+ for (const auto BI : *SortedGraph)
+ VisitOrder[BI->getBlockID()] = VisitOrderCounter++;
+ }
+
+ bool allBackEdgesVisited(const CFGBlock *CurrBlock,
+ const CFGBlock *TargetBlock);
+
+ void addInfo(const CFGBlock *Block, ConsumedStateMap *StateMap,
+ std::unique_ptr<ConsumedStateMap> &OwnedStateMap);
+ void addInfo(const CFGBlock *Block,
+ std::unique_ptr<ConsumedStateMap> StateMap);
+
+ ConsumedStateMap* borrowInfo(const CFGBlock *Block);
+
+ void discardInfo(const CFGBlock *Block);
+
+ std::unique_ptr<ConsumedStateMap> getInfo(const CFGBlock *Block);
+
+ bool isBackEdge(const CFGBlock *From, const CFGBlock *To);
+ bool isBackEdgeTarget(const CFGBlock *Block);
+ };
+
+ /// A class that handles the analysis of uniqueness violations.
+ class ConsumedAnalyzer {
+ ConsumedBlockInfo BlockInfo;
+ std::unique_ptr<ConsumedStateMap> CurrStates;
+
+ ConsumedState ExpectedReturnState;
+
+ void determineExpectedReturnState(AnalysisDeclContext &AC,
+ const FunctionDecl *D);
+ bool splitState(const CFGBlock *CurrBlock,
+ const ConsumedStmtVisitor &Visitor);
+
+ public:
+ ConsumedWarningsHandlerBase &WarningsHandler;
+
+ ConsumedAnalyzer(ConsumedWarningsHandlerBase &WarningsHandler)
+ : WarningsHandler(WarningsHandler) {}
+
+ ConsumedState getExpectedReturnState() const { return ExpectedReturnState; }
+
+ /// Check a function's CFG for consumed violations.
+ ///
+ /// We traverse the blocks in the CFG, keeping track of the state of each
+ /// value who's type has uniquness annotations. If methods are invoked in
+ /// the wrong state a warning is issued. Each block in the CFG is traversed
+ /// exactly once.
+ void run(AnalysisDeclContext &AC);
+ };
+
+} // namespace consumed
+
+} // namespace clang
+
+#endif // LLVM_CLANG_ANALYSIS_ANALYSES_CONSUMED_H
+
+#ifdef __GNUC__
+#pragma GCC diagnostic pop
+#endif