/// type specified.
UnionParsedType TrailingReturnType;
+ /// If HasTrailingReturnType is true, this is the location of the trailing
+ /// return type.
+ unsigned TrailingReturnTypeLoc;
+
/// Reset the parameter list to having zero parameters.
///
/// This is used in various places for error recovery.
/// Get the trailing-return-type for this function declarator.
ParsedType getTrailingReturnType() const { return TrailingReturnType; }
+
+ /// Get the trailing-return-type location for this function declarator.
+ SourceLocation getTrailingReturnTypeLoc() const {
+ return SourceLocation::getFromRawEncoding(TrailingReturnTypeLoc);
+ }
};
struct BlockPointerTypeInfo {
Declarator &TheDeclarator,
TypeResult TrailingReturnType =
TypeResult(),
+ SourceLocation TrailingReturnTypeLoc =
+ SourceLocation(),
DeclSpec *MethodQualifiers = nullptr);
/// Return a DeclaratorChunk for a block.
CachedTokens *ExceptionSpecTokens = nullptr;
ParsedAttributesWithRange FnAttrs(AttrFactory);
TypeResult TrailingReturnType;
+ SourceLocation TrailingReturnTypeLoc;
/* LocalEndLoc is the end location for the local FunctionTypeLoc.
EndLoc is the end location for the function declarator.
SourceRange Range;
TrailingReturnType =
ParseTrailingReturnType(Range, D.mayBeFollowedByCXXDirectInit());
+ TrailingReturnTypeLoc = Range.getBegin();
EndLoc = Range.getEnd();
}
} else if (standardAttributesAllowed()) {
DynamicExceptionRanges.data(), DynamicExceptions.size(),
NoexceptExpr.isUsable() ? NoexceptExpr.get() : nullptr,
ExceptionSpecTokens, DeclsInPrototype, StartLoc,
- LocalEndLoc, D, TrailingReturnType, &DS),
+ LocalEndLoc, D, TrailingReturnType, TrailingReturnTypeLoc,
+ &DS),
std::move(FnAttrs), EndLoc);
}
auto &FunctionChunk = D.getFunctionTypeInfo();
FunctionChunk.HasTrailingReturnType = TrailingReturnType.isUsable();
FunctionChunk.TrailingReturnType = TrailingReturnType.get();
+ FunctionChunk.TrailingReturnTypeLoc = Range.getBegin().getRawEncoding();
} else
SkipUntil({tok::equal, tok::l_brace, tok::arrow, tok::kw_try, tok::comma},
StopAtSemi | StopBeforeMatch);
}
TypeResult TrailingReturnType;
+ SourceLocation TrailingReturnTypeLoc;
if (Tok.is(tok::l_paren)) {
ParseScope PrototypeScope(this,
Scope::FunctionPrototypeScope |
SourceRange Range;
TrailingReturnType =
ParseTrailingReturnType(Range, /*MayBeFollowedByDirectInit*/ false);
+ TrailingReturnTypeLoc = Range.getBegin();
if (Range.getEnd().isValid())
DeclEndLoc = Range.getEnd();
}
NoexceptExpr.isUsable() ? NoexceptExpr.get() : nullptr,
/*ExceptionSpecTokens*/ nullptr,
/*DeclsInPrototype=*/None, LParenLoc, FunLocalRangeEnd, D,
- TrailingReturnType, &DS),
+ TrailingReturnType, TrailingReturnTypeLoc, &DS),
std::move(Attr), DeclEndLoc);
// Parse requires-clause[opt].
SourceLocation LocalRangeEnd,
Declarator &TheDeclarator,
TypeResult TrailingReturnType,
+ SourceLocation
+ TrailingReturnTypeLoc,
DeclSpec *MethodQualifiers) {
assert(!(MethodQualifiers && MethodQualifiers->getTypeQualifiers() & DeclSpec::TQ_atomic) &&
"function cannot have _Atomic qualifier");
I.Fun.HasTrailingReturnType = TrailingReturnType.isUsable() ||
TrailingReturnType.isInvalid();
I.Fun.TrailingReturnType = TrailingReturnType.get();
+ I.Fun.TrailingReturnTypeLoc = TrailingReturnTypeLoc.getRawEncoding();
I.Fun.MethodQualifiers = nullptr;
I.Fun.QualAttrFactory = nullptr;
static void diagnoseRedundantReturnTypeQualifiers(Sema &S, QualType RetTy,
Declarator &D,
unsigned FunctionChunkIndex) {
- if (D.getTypeObject(FunctionChunkIndex).Fun.hasTrailingReturnType()) {
- // FIXME: TypeSourceInfo doesn't preserve location information for
- // qualifiers.
+ const DeclaratorChunk::FunctionTypeInfo &FTI =
+ D.getTypeObject(FunctionChunkIndex).Fun;
+ if (FTI.hasTrailingReturnType()) {
S.diagnoseIgnoredQualifiers(diag::warn_qual_return_type,
RetTy.getLocalCVRQualifiers(),
- D.getIdentifierLoc());
+ FTI.getTrailingReturnTypeLoc());
return;
}
int
atomic();
-auto
- trailing_return_type() -> // expected-warning {{'const' type qualifier on return type has no effect}}
- const int;
+auto trailing_return_type() ->
+ const int; // expected-warning {{'const' type qualifier on return type has no effect}}
+
+auto trailing_return_type_lambda = [](const int &x) ->
+ const int // expected-warning {{'const' type qualifier on return type has no effect}}
+ { return x; };
const int ret_array()[4]; // expected-error {{cannot return array}}
}