xref: /minix3/external/bsd/llvm/dist/clang/include/clang/AST/ASTLambda.h (revision 0a6a1f1d05b60e214de2f05a7310ddd1f0e590e7)
1f4a2713aSLionel Sambuc //===--- ASTLambda.h - Lambda Helper Functions --------------*- C++ -*-===//
2f4a2713aSLionel Sambuc //
3f4a2713aSLionel Sambuc //                     The LLVM Compiler Infrastructure
4f4a2713aSLionel Sambuc //
5f4a2713aSLionel Sambuc // This file is distributed under the University of Illinois Open Source
6f4a2713aSLionel Sambuc // License. See LICENSE.TXT for details.
7f4a2713aSLionel Sambuc //
8f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
9f4a2713aSLionel Sambuc ///
10f4a2713aSLionel Sambuc /// \file
11f4a2713aSLionel Sambuc /// \brief This file provides some common utility functions for processing
12f4a2713aSLionel Sambuc /// Lambda related AST Constructs.
13f4a2713aSLionel Sambuc ///
14f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
15f4a2713aSLionel Sambuc 
16*0a6a1f1dSLionel Sambuc #ifndef LLVM_CLANG_AST_ASTLAMBDA_H
17*0a6a1f1dSLionel Sambuc #define LLVM_CLANG_AST_ASTLAMBDA_H
18f4a2713aSLionel Sambuc 
19f4a2713aSLionel Sambuc #include "clang/AST/DeclCXX.h"
20f4a2713aSLionel Sambuc #include "clang/AST/DeclTemplate.h"
21f4a2713aSLionel Sambuc 
22f4a2713aSLionel Sambuc namespace clang {
getLambdaStaticInvokerName()23f4a2713aSLionel Sambuc inline StringRef getLambdaStaticInvokerName() {
24f4a2713aSLionel Sambuc   return "__invoke";
25f4a2713aSLionel Sambuc }
26f4a2713aSLionel Sambuc // This function returns true if M is a specialization, a template,
27f4a2713aSLionel Sambuc // or a non-generic lambda call operator.
isLambdaCallOperator(const CXXMethodDecl * MD)28f4a2713aSLionel Sambuc inline bool isLambdaCallOperator(const CXXMethodDecl *MD) {
29f4a2713aSLionel Sambuc   const CXXRecordDecl *LambdaClass = MD->getParent();
30f4a2713aSLionel Sambuc   if (!LambdaClass || !LambdaClass->isLambda()) return false;
31f4a2713aSLionel Sambuc   return MD->getOverloadedOperator() == OO_Call;
32f4a2713aSLionel Sambuc }
33f4a2713aSLionel Sambuc 
isLambdaCallOperator(const DeclContext * DC)34f4a2713aSLionel Sambuc inline bool isLambdaCallOperator(const DeclContext *DC) {
35f4a2713aSLionel Sambuc   if (!DC || !isa<CXXMethodDecl>(DC)) return false;
36f4a2713aSLionel Sambuc   return isLambdaCallOperator(cast<CXXMethodDecl>(DC));
37f4a2713aSLionel Sambuc }
38f4a2713aSLionel Sambuc 
isGenericLambdaCallOperatorSpecialization(const CXXMethodDecl * MD)39*0a6a1f1dSLionel Sambuc inline bool isGenericLambdaCallOperatorSpecialization(const CXXMethodDecl *MD) {
40f4a2713aSLionel Sambuc   if (!MD) return false;
41*0a6a1f1dSLionel Sambuc   const CXXRecordDecl *LambdaClass = MD->getParent();
42f4a2713aSLionel Sambuc   if (LambdaClass && LambdaClass->isGenericLambda())
43f4a2713aSLionel Sambuc     return isLambdaCallOperator(MD) &&
44f4a2713aSLionel Sambuc                     MD->isFunctionTemplateSpecialization();
45f4a2713aSLionel Sambuc   return false;
46f4a2713aSLionel Sambuc }
47f4a2713aSLionel Sambuc 
isLambdaConversionOperator(CXXConversionDecl * C)48f4a2713aSLionel Sambuc inline bool isLambdaConversionOperator(CXXConversionDecl *C) {
49f4a2713aSLionel Sambuc   return C ? C->getParent()->isLambda() : false;
50f4a2713aSLionel Sambuc }
51f4a2713aSLionel Sambuc 
isLambdaConversionOperator(Decl * D)52f4a2713aSLionel Sambuc inline bool isLambdaConversionOperator(Decl *D) {
53f4a2713aSLionel Sambuc   if (!D) return false;
54f4a2713aSLionel Sambuc   if (CXXConversionDecl *Conv = dyn_cast<CXXConversionDecl>(D))
55f4a2713aSLionel Sambuc     return isLambdaConversionOperator(Conv);
56f4a2713aSLionel Sambuc   if (FunctionTemplateDecl *F = dyn_cast<FunctionTemplateDecl>(D))
57f4a2713aSLionel Sambuc     if (CXXConversionDecl *Conv =
58f4a2713aSLionel Sambuc         dyn_cast_or_null<CXXConversionDecl>(F->getTemplatedDecl()))
59f4a2713aSLionel Sambuc       return isLambdaConversionOperator(Conv);
60f4a2713aSLionel Sambuc   return false;
61f4a2713aSLionel Sambuc }
62f4a2713aSLionel Sambuc 
isGenericLambdaCallOperatorSpecialization(DeclContext * DC)63f4a2713aSLionel Sambuc inline bool isGenericLambdaCallOperatorSpecialization(DeclContext *DC) {
64f4a2713aSLionel Sambuc   return isGenericLambdaCallOperatorSpecialization(
65f4a2713aSLionel Sambuc                                           dyn_cast<CXXMethodDecl>(DC));
66f4a2713aSLionel Sambuc }
67f4a2713aSLionel Sambuc 
68f4a2713aSLionel Sambuc 
69f4a2713aSLionel Sambuc // This returns the parent DeclContext ensuring that the correct
70f4a2713aSLionel Sambuc // parent DeclContext is returned for Lambdas
getLambdaAwareParentOfDeclContext(DeclContext * DC)71f4a2713aSLionel Sambuc inline DeclContext *getLambdaAwareParentOfDeclContext(DeclContext *DC) {
72f4a2713aSLionel Sambuc   if (isLambdaCallOperator(DC))
73f4a2713aSLionel Sambuc     return DC->getParent()->getParent();
74f4a2713aSLionel Sambuc   else
75f4a2713aSLionel Sambuc     return DC->getParent();
76f4a2713aSLionel Sambuc }
77f4a2713aSLionel Sambuc 
78f4a2713aSLionel Sambuc } // clang
79f4a2713aSLionel Sambuc 
80*0a6a1f1dSLionel Sambuc #endif
81