aboutsummaryrefslogtreecommitdiff
path: root/lib/Sema
diff options
context:
space:
mode:
Diffstat (limited to 'lib/Sema')
-rw-r--r--lib/Sema/Sema.cpp9
-rw-r--r--lib/Sema/SemaDecl.cpp2
-rw-r--r--lib/Sema/SemaDeclCXX.cpp2
-rw-r--r--lib/Sema/SemaExpr.cpp4
-rw-r--r--lib/Sema/SemaExprCXX.cpp72
5 files changed, 71 insertions, 18 deletions
diff --git a/lib/Sema/Sema.cpp b/lib/Sema/Sema.cpp
index c8199042b7..6a77d8c673 100644
--- a/lib/Sema/Sema.cpp
+++ b/lib/Sema/Sema.cpp
@@ -55,6 +55,7 @@ void FunctionScopeInfo::Clear() {
}
BlockScopeInfo::~BlockScopeInfo() { }
+LambdaScopeInfo::~LambdaScopeInfo() { }
PrintingPolicy Sema::getPrintingPolicy() const {
PrintingPolicy Policy = Context.getPrintingPolicy();
@@ -828,8 +829,12 @@ void Sema::PushBlockScope(Scope *BlockScope, BlockDecl *Block) {
BlockScope, Block));
}
-void Sema::PopFunctionOrBlockScope(const AnalysisBasedWarnings::Policy *WP,
- const Decl *D, const BlockExpr *blkExpr) {
+void Sema::PushLambdaScope(CXXRecordDecl *Lambda) {
+ FunctionScopes.push_back(new LambdaScopeInfo(getDiagnostics(), Lambda));
+}
+
+void Sema::PopFunctionScopeInfo(const AnalysisBasedWarnings::Policy *WP,
+ const Decl *D, const BlockExpr *blkExpr) {
FunctionScopeInfo *Scope = FunctionScopes.pop_back_val();
assert(!FunctionScopes.empty() && "mismatched push/pop!");
diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp
index f82026f89f..8353c087d5 100644
--- a/lib/Sema/SemaDecl.cpp
+++ b/lib/Sema/SemaDecl.cpp
@@ -7207,7 +7207,7 @@ Decl *Sema::ActOnFinishFunctionBody(Decl *dcl, Stmt *Body,
if (!IsInstantiation)
PopDeclContext();
- PopFunctionOrBlockScope(ActivePolicy, dcl);
+ PopFunctionScopeInfo(ActivePolicy, dcl);
// If any errors have occurred, clear out any temporaries that may have
// been leftover. This ensures that these temporaries won't be picked up for
diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp
index ad327ac755..46a47a2215 100644
--- a/lib/Sema/SemaDeclCXX.cpp
+++ b/lib/Sema/SemaDeclCXX.cpp
@@ -6784,7 +6784,7 @@ namespace {
~ImplicitlyDefinedFunctionScope() {
S.PopExpressionEvaluationContext();
- S.PopFunctionOrBlockScope();
+ S.PopFunctionScopeInfo();
}
};
}
diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp
index 126468ee35..8554e78636 100644
--- a/lib/Sema/SemaExpr.cpp
+++ b/lib/Sema/SemaExpr.cpp
@@ -8839,7 +8839,7 @@ void Sema::ActOnBlockError(SourceLocation CaretLoc, Scope *CurScope) {
// Pop off CurBlock, handle nested blocks.
PopDeclContext();
- PopFunctionOrBlockScope();
+ PopFunctionScopeInfo();
}
/// ActOnBlockStmtExpr - This is called when the body of a block statement
@@ -8931,7 +8931,7 @@ ExprResult Sema::ActOnBlockStmtExpr(SourceLocation CaretLoc,
BlockExpr *Result = new (Context) BlockExpr(BSI->TheDecl, BlockTy);
const AnalysisBasedWarnings::Policy &WP = AnalysisWarnings.getDefaultPolicy();
- PopFunctionOrBlockScope(&WP, Result->getBlockDecl(), Result);
+ PopFunctionScopeInfo(&WP, Result->getBlockDecl(), Result);
// If the block isn't obviously global, i.e. it captures anything at
// all, mark this full-expression as needing a cleanup.
diff --git a/lib/Sema/SemaExprCXX.cpp b/lib/Sema/SemaExprCXX.cpp
index e53e5cda62..fd47dc75b2 100644
--- a/lib/Sema/SemaExprCXX.cpp
+++ b/lib/Sema/SemaExprCXX.cpp
@@ -4778,20 +4778,68 @@ Sema::CheckMicrosoftIfExistsSymbol(Scope *S, SourceLocation KeywordLoc,
// Lambdas.
//===----------------------------------------------------------------------===//
-void Sema::ActOnLambdaStart(SourceLocation StartLoc, Scope *CurScope) {
- // FIXME: Add lambda-scope
- // FIXME: PushDeclContext
+void Sema::ActOnStartOfLambdaDefinition(LambdaIntroducer &Intro,
+ Declarator &ParamInfo,
+ Scope *CurScope) {
+ DeclContext *DC = CurContext;
+ while (!(DC->isFunctionOrMethod() || DC->isRecord() || DC->isNamespace()))
+ DC = DC->getParent();
+
+ // Start constructing the lambda class.
+ CXXRecordDecl *Class = CXXRecordDecl::Create(Context, TTK_Class, DC,
+ Intro.Range.getBegin(),
+ /*IdLoc=*/SourceLocation(),
+ /*Id=*/0);
+ Class->startDefinition();
+ CurContext->addDecl(Class);
+
+ // Build the call operator; we don't really have all the relevant information
+ // at this point, but we need something to attach child declarations to.
+ TypeSourceInfo *MethodTyInfo;
+ MethodTyInfo = GetTypeForDeclarator(ParamInfo, CurScope);
+
+ DeclarationName MethodName
+ = Context.DeclarationNames.getCXXOperatorName(OO_Call);
+ CXXMethodDecl *Method
+ = CXXMethodDecl::Create(Context,
+ Class,
+ ParamInfo.getSourceRange().getEnd(),
+ DeclarationNameInfo(MethodName,
+ /*NameLoc=*/SourceLocation()),
+ MethodTyInfo->getType(),
+ MethodTyInfo,
+ /*isStatic=*/false,
+ SC_None,
+ /*isInline=*/true,
+ /*isConstExpr=*/false,
+ ParamInfo.getSourceRange().getEnd());
+ Method->setAccess(AS_public);
+ Class->addDecl(Method);
+ Method->setLexicalDeclContext(DC); // FIXME: Is this really correct?
+
+ // Set the parameters on the decl, if specified.
+ if (isa<FunctionProtoTypeLoc>(MethodTyInfo->getTypeLoc())) {
+ FunctionProtoTypeLoc Proto =
+ cast<FunctionProtoTypeLoc>(MethodTyInfo->getTypeLoc());
+ Method->setParams(Proto.getParams());
+ CheckParmsForFunctionDef(Method->param_begin(),
+ Method->param_end(),
+ /*CheckParameterNames=*/false);
+ }
+
+ ProcessDeclAttributes(CurScope, Method, ParamInfo);
+
+ // FIXME: There's a bunch of missing checking etc;
+ // see ActOnBlockArguments
+
+ // Introduce the lambda scope.
+ PushLambdaScope(Class);
// Enter a new evaluation context to insulate the block from any
// cleanups from the enclosing full-expression.
- PushExpressionEvaluationContext(PotentiallyEvaluated);
-}
-
-void Sema::ActOnLambdaArguments(Declarator &ParamInfo, Scope *CurScope) {
- TypeSourceInfo *MethodTyInfo;
- MethodTyInfo = GetTypeForDeclarator(ParamInfo, CurScope);
+ PushExpressionEvaluationContext(PotentiallyEvaluated);
- // FIXME: Build CXXMethodDecl
+ PushDeclContext(CurScope, Method);
}
void Sema::ActOnLambdaError(SourceLocation StartLoc, Scope *CurScope) {
@@ -4800,8 +4848,8 @@ void Sema::ActOnLambdaError(SourceLocation StartLoc, Scope *CurScope) {
PopExpressionEvaluationContext();
// Leave the context of the lambda.
- // FIXME: PopDeclContext
- // FIXME: Pop lambda-scope
+ PopDeclContext();
+ PopFunctionScopeInfo();
}
ExprResult Sema::ActOnLambdaExpr(SourceLocation StartLoc,