Line data Source code
1 : //===--- LambdaCapture.h - Types for C++ Lambda Captures --------*- C++ -*-===//
2 : //
3 : // The LLVM Compiler Infrastructure
4 : //
5 : // This file is distributed under the University of Illinois Open Source
6 : // License. See LICENSE.TXT for details.
7 : //
8 : //===----------------------------------------------------------------------===//
9 : ///
10 : /// \file
11 : /// \brief Defines the LambdaCapture class.
12 : ///
13 : //===----------------------------------------------------------------------===//
14 :
15 : #ifndef LLVM_CLANG_AST_LAMBDACAPTURE_H
16 : #define LLVM_CLANG_AST_LAMBDACAPTURE_H
17 :
18 : #include "clang/AST/Decl.h"
19 : #include "clang/Basic/Lambda.h"
20 : #include "llvm/ADT/PointerIntPair.h"
21 :
22 : namespace clang {
23 :
24 : /// \brief Describes the capture of a variable or of \c this, or of a
25 : /// C++1y init-capture.
26 : class LambdaCapture {
27 : enum {
28 : /// \brief Flag used by the Capture class to indicate that the given
29 : /// capture was implicit.
30 : Capture_Implicit = 0x01,
31 :
32 : /// \brief Flag used by the Capture class to indicate that the
33 : /// given capture was by-copy.
34 : ///
35 : /// This includes the case of a non-reference init-capture.
36 : Capture_ByCopy = 0x02
37 : };
38 :
39 : llvm::PointerIntPair<Decl *, 2> DeclAndBits;
40 : SourceLocation Loc;
41 : SourceLocation EllipsisLoc;
42 :
43 : friend class ASTStmtReader;
44 : friend class ASTStmtWriter;
45 :
46 : public:
47 : /// \brief Create a new capture of a variable or of \c this.
48 : ///
49 : /// \param Loc The source location associated with this capture.
50 : ///
51 : /// \param Kind The kind of capture (this, byref, bycopy), which must
52 : /// not be init-capture.
53 : ///
54 : /// \param Implicit Whether the capture was implicit or explicit.
55 : ///
56 : /// \param Var The local variable being captured, or null if capturing
57 : /// \c this.
58 : ///
59 : /// \param EllipsisLoc The location of the ellipsis (...) for a
60 : /// capture that is a pack expansion, or an invalid source
61 : /// location to indicate that this is not a pack expansion.
62 : LambdaCapture(SourceLocation Loc, bool Implicit, LambdaCaptureKind Kind,
63 : VarDecl *Var = nullptr,
64 : SourceLocation EllipsisLoc = SourceLocation());
65 :
66 : /// \brief Determine the kind of capture.
67 : LambdaCaptureKind getCaptureKind() const;
68 :
69 : /// \brief Determine whether this capture handles the C++ \c this
70 : /// pointer.
71 : bool capturesThis() const {
72 : return (DeclAndBits.getPointer() == nullptr) &&
73 : !(DeclAndBits.getInt() & Capture_ByCopy);
74 : }
75 :
76 : /// \brief Determine whether this capture handles a variable.
77 : bool capturesVariable() const {
78 0 : return dyn_cast_or_null<VarDecl>(DeclAndBits.getPointer());
79 : }
80 :
81 : /// \brief Determine whether this captures a variable length array bound
82 : /// expression.
83 : bool capturesVLAType() const {
84 : return (DeclAndBits.getPointer() == nullptr) &&
85 : (DeclAndBits.getInt() & Capture_ByCopy);
86 : }
87 :
88 : /// \brief Retrieve the declaration of the local variable being
89 : /// captured.
90 : ///
91 : /// This operation is only valid if this capture is a variable capture
92 : /// (other than a capture of \c this).
93 : VarDecl *getCapturedVar() const {
94 0 : assert(capturesVariable() && "No variable available for 'this' capture");
95 0 : return cast<VarDecl>(DeclAndBits.getPointer());
96 : }
97 :
98 : /// \brief Determine whether this was an implicit capture (not
99 : /// written between the square brackets introducing the lambda).
100 : bool isImplicit() const { return DeclAndBits.getInt() & Capture_Implicit; }
101 :
102 : /// \brief Determine whether this was an explicit capture (written
103 : /// between the square brackets introducing the lambda).
104 : bool isExplicit() const { return !isImplicit(); }
105 :
106 : /// \brief Retrieve the source location of the capture.
107 : ///
108 : /// For an explicit capture, this returns the location of the
109 : /// explicit capture in the source. For an implicit capture, this
110 : /// returns the location at which the variable or \c this was first
111 : /// used.
112 : SourceLocation getLocation() const { return Loc; }
113 :
114 : /// \brief Determine whether this capture is a pack expansion,
115 : /// which captures a function parameter pack.
116 : bool isPackExpansion() const { return EllipsisLoc.isValid(); }
117 :
118 : /// \brief Retrieve the location of the ellipsis for a capture
119 : /// that is a pack expansion.
120 : SourceLocation getEllipsisLoc() const {
121 : assert(isPackExpansion() && "No ellipsis location for a non-expansion");
122 : return EllipsisLoc;
123 : }
124 : };
125 :
126 : } // end namespace clang
127 :
128 : #endif // LLVM_CLANG_AST_LAMBDACAPTURE_H
|