本文整理汇总了C++中TypeResult类的典型用法代码示例。如果您正苦于以下问题:C++ TypeResult类的具体用法?C++ TypeResult怎么用?C++ TypeResult使用的例子?那么恭喜您, 这里精选的类代码示例或许可以为您提供帮助。
在下文中一共展示了TypeResult类的9个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。
示例1: assert
/// \brief Replaces a template-id annotation token with a type
/// annotation token.
///
/// If there was a failure when forming the type from the template-id,
/// a type annotation token will still be created, but will have a
/// NULL type pointer to signify an error.
void Parser::AnnotateTemplateIdTokenAsType() {
assert(Tok.is(tok::annot_template_id) && "Requires template-id tokens");
TemplateIdAnnotation *TemplateId
= static_cast<TemplateIdAnnotation *>(Tok.getAnnotationValue());
assert((TemplateId->Kind == TNK_Type_template ||
TemplateId->Kind == TNK_Dependent_template_name) &&
"Only works for type and dependent templates");
ASTTemplateArgsPtr TemplateArgsPtr(Actions,
TemplateId->getTemplateArgs(),
TemplateId->NumArgs);
TypeResult Type
= Actions.ActOnTemplateIdType(TemplateId->SS,
TemplateId->Template,
TemplateId->TemplateNameLoc,
TemplateId->LAngleLoc,
TemplateArgsPtr,
TemplateId->RAngleLoc);
// Create the new "type" annotation token.
Tok.setKind(tok::annot_typename);
setTypeAnnotation(Tok, Type.isInvalid() ? ParsedType() : Type.get());
if (TemplateId->SS.isNotEmpty()) // it was a C++ qualified type name.
Tok.setLocation(TemplateId->SS.getBeginLoc());
// End location stays the same
// Replace the template-id annotation token, and possible the scope-specifier
// that precedes it, with the typename annotation token.
PP.AnnotateCachedTokens(Tok);
TemplateId->Destroy();
}
示例2: ParseTypeName
/// ParseTemplateArgument - Parse a C++ template argument (C++ [temp.names]).
///
/// template-argument: [C++ 14.2]
/// constant-expression
/// type-id
/// id-expression
ParsedTemplateArgument Parser::ParseTemplateArgument() {
// C++ [temp.arg]p2:
// In a template-argument, an ambiguity between a type-id and an
// expression is resolved to a type-id, regardless of the form of
// the corresponding template-parameter.
//
// Therefore, we initially try to parse a type-id.
if (isCXXTypeId(TypeIdAsTemplateArgument)) {
SourceLocation Loc = Tok.getLocation();
TypeResult TypeArg = ParseTypeName(/*Range=*/0,
Declarator::TemplateTypeArgContext);
if (TypeArg.isInvalid())
return ParsedTemplateArgument();
return ParsedTemplateArgument(ParsedTemplateArgument::Type,
TypeArg.get().getAsOpaquePtr(),
Loc);
}
// Try to parse a template template argument.
{
TentativeParsingAction TPA(*this);
ParsedTemplateArgument TemplateTemplateArgument
= ParseTemplateTemplateArgument();
if (!TemplateTemplateArgument.isInvalid()) {
TPA.Commit();
return TemplateTemplateArgument;
}
// Revert this tentative parse to parse a non-type template argument.
TPA.Revert();
}
// Parse a non-type template argument.
SourceLocation Loc = Tok.getLocation();
ExprResult ExprArg = ParseConstantExpression();
if (ExprArg.isInvalid() || !ExprArg.get())
return ParsedTemplateArgument();
return ParsedTemplateArgument(ParsedTemplateArgument::NonType,
ExprArg.release(), Loc);
}
示例3: switch
ParsedTemplateArgument
Sema::ActOnPackExpansion(const ParsedTemplateArgument &Arg,
SourceLocation EllipsisLoc) {
if (Arg.isInvalid())
return Arg;
switch (Arg.getKind()) {
case ParsedTemplateArgument::Type: {
TypeResult Result = ActOnPackExpansion(Arg.getAsType(), EllipsisLoc);
if (Result.isInvalid())
return ParsedTemplateArgument();
return ParsedTemplateArgument(Arg.getKind(), Result.get().getAsOpaquePtr(),
Arg.getLocation());
}
case ParsedTemplateArgument::NonType: {
ExprResult Result = ActOnPackExpansion(Arg.getAsExpr(), EllipsisLoc);
if (Result.isInvalid())
return ParsedTemplateArgument();
return ParsedTemplateArgument(Arg.getKind(), Result.get(),
Arg.getLocation());
}
case ParsedTemplateArgument::Template:
if (!Arg.getAsTemplate().get().containsUnexpandedParameterPack()) {
SourceRange R(Arg.getLocation());
if (Arg.getScopeSpec().isValid())
R.setBegin(Arg.getScopeSpec().getBeginLoc());
Diag(EllipsisLoc, diag::err_pack_expansion_without_parameter_packs)
<< R;
return ParsedTemplateArgument();
}
return Arg.getTemplatePackExpansion(EllipsisLoc);
}
llvm_unreachable("Unhandled template argument kind?");
return ParsedTemplateArgument();
}
示例4: Error
/// ParseMatchedBinaryArgs - Parse a pair of arguments who are
/// expected to be of the same type. Upon return, if both LHS and RHS
/// are valid then they are guaranteed to have the same type.
///
/// Name - The name token of the expression, for diagnostics.
/// ExpectType - The expected type of the arguments, if known.
void ParserImpl::ParseMatchedBinaryArgs(const Token &Name,
TypeResult ExpectType,
ExprResult &LHS, ExprResult &RHS) {
if (Tok.kind == Token::RParen) {
Error("unexpected end of arguments.", Name);
ConsumeRParen();
return;
}
// Avoid NumberOrExprResult overhead and give more precise
// diagnostics when we know the type.
if (ExpectType.isValid()) {
LHS = ParseExpr(ExpectType);
if (Tok.kind == Token::RParen) {
Error("unexpected end of arguments.", Name);
ConsumeRParen();
return;
}
RHS = ParseExpr(ExpectType);
} else {
NumberOrExprResult LHS_NOE = ParseNumberOrExpr();
if (Tok.kind == Token::RParen) {
Error("unexpected end of arguments.", Name);
ConsumeRParen();
return;
}
if (LHS_NOE.isNumber()) {
NumberOrExprResult RHS_NOE = ParseNumberOrExpr();
if (RHS_NOE.isNumber()) {
Error("ambiguous arguments to expression.", Name);
} else {
RHS = RHS_NOE.getExpr();
if (RHS.isValid())
LHS = ParseNumberToken(RHS.get()->getWidth(), LHS_NOE.getNumber());
}
} else {
LHS = LHS_NOE.getExpr();
if (!LHS.isValid()) {
// FIXME: Should suppress ambiguity warnings here.
RHS = ParseExpr(TypeResult());
} else {
RHS = ParseExpr(LHS.get()->getWidth());
}
}
}
ExpectRParen("unexpected argument to expression.");
}
示例5: getFunction
/// DeclaratorChunk::getFunction - Return a DeclaratorChunk for a function.
/// "TheDeclarator" is the declarator that this will be added to.
DeclaratorChunk DeclaratorChunk::getFunction(bool hasProto,
bool isAmbiguous,
SourceLocation LParenLoc,
ParamInfo *Params,
unsigned NumParams,
SourceLocation EllipsisLoc,
SourceLocation RParenLoc,
unsigned TypeQuals,
bool RefQualifierIsLvalueRef,
SourceLocation RefQualifierLoc,
SourceLocation ConstQualifierLoc,
SourceLocation
VolatileQualifierLoc,
SourceLocation
RestrictQualifierLoc,
SourceLocation MutableLoc,
ExceptionSpecificationType
ESpecType,
SourceLocation ESpecLoc,
ParsedType *Exceptions,
SourceRange *ExceptionRanges,
unsigned NumExceptions,
Expr *NoexceptExpr,
CachedTokens *ExceptionSpecTokens,
SourceLocation LocalRangeBegin,
SourceLocation LocalRangeEnd,
Declarator &TheDeclarator,
TypeResult TrailingReturnType) {
assert(!(TypeQuals & DeclSpec::TQ_atomic) &&
"function cannot have _Atomic qualifier");
DeclaratorChunk I;
I.Kind = Function;
I.Loc = LocalRangeBegin;
I.EndLoc = LocalRangeEnd;
I.Fun.AttrList = nullptr;
I.Fun.hasPrototype = hasProto;
I.Fun.isVariadic = EllipsisLoc.isValid();
I.Fun.isAmbiguous = isAmbiguous;
I.Fun.LParenLoc = LParenLoc.getRawEncoding();
I.Fun.EllipsisLoc = EllipsisLoc.getRawEncoding();
I.Fun.RParenLoc = RParenLoc.getRawEncoding();
I.Fun.DeleteParams = false;
I.Fun.TypeQuals = TypeQuals;
I.Fun.NumParams = NumParams;
I.Fun.Params = nullptr;
I.Fun.RefQualifierIsLValueRef = RefQualifierIsLvalueRef;
I.Fun.RefQualifierLoc = RefQualifierLoc.getRawEncoding();
I.Fun.ConstQualifierLoc = ConstQualifierLoc.getRawEncoding();
I.Fun.VolatileQualifierLoc = VolatileQualifierLoc.getRawEncoding();
I.Fun.RestrictQualifierLoc = RestrictQualifierLoc.getRawEncoding();
I.Fun.MutableLoc = MutableLoc.getRawEncoding();
I.Fun.ExceptionSpecType = ESpecType;
I.Fun.ExceptionSpecLoc = ESpecLoc.getRawEncoding();
I.Fun.NumExceptions = 0;
I.Fun.Exceptions = nullptr;
I.Fun.NoexceptExpr = nullptr;
I.Fun.HasTrailingReturnType = TrailingReturnType.isUsable() ||
TrailingReturnType.isInvalid();
I.Fun.TrailingReturnType = TrailingReturnType.get();
assert(I.Fun.TypeQuals == TypeQuals && "bitfield overflow");
assert(I.Fun.ExceptionSpecType == ESpecType && "bitfield overflow");
// new[] a parameter array if needed.
if (NumParams) {
// If the 'InlineParams' in Declarator is unused and big enough, put our
// parameter list there (in an effort to avoid new/delete traffic). If it
// is already used (consider a function returning a function pointer) or too
// small (function with too many parameters), go to the heap.
if (!TheDeclarator.InlineParamsUsed &&
NumParams <= llvm::array_lengthof(TheDeclarator.InlineParams)) {
I.Fun.Params = TheDeclarator.InlineParams;
I.Fun.DeleteParams = false;
TheDeclarator.InlineParamsUsed = true;
} else {
I.Fun.Params = new DeclaratorChunk::ParamInfo[NumParams];
I.Fun.DeleteParams = true;
}
memcpy(I.Fun.Params, Params, sizeof(Params[0]) * NumParams);
}
// Check what exception specification information we should actually store.
switch (ESpecType) {
default: break; // By default, save nothing.
case EST_Dynamic:
// new[] an exception array if needed
if (NumExceptions) {
I.Fun.NumExceptions = NumExceptions;
I.Fun.Exceptions = new DeclaratorChunk::TypeAndRange[NumExceptions];
for (unsigned i = 0; i != NumExceptions; ++i) {
I.Fun.Exceptions[i].Ty = Exceptions[i];
I.Fun.Exceptions[i].Range = ExceptionRanges[i];
}
}
break;
case EST_ComputedNoexcept:
//.........这里部分代码省略.........
示例6: ConsumeToken
//.........这里部分代码省略.........
}
// If the receiver was an expression, we still don't know
// whether we have a message send or an array designator; just
// adopt the expression for further analysis below.
// FIXME: potentially-potentially evaluated expression above?
Idx = ExprResult(static_cast<Expr*>(TypeOrExpr));
} else if (getLangOpts().ObjC && Tok.is(tok::identifier)) {
IdentifierInfo *II = Tok.getIdentifierInfo();
SourceLocation IILoc = Tok.getLocation();
ParsedType ReceiverType;
// Three cases. This is a message send to a type: [type foo]
// This is a message send to super: [super foo]
// This is a message sent to an expr: [super.bar foo]
switch (Actions.getObjCMessageKind(
getCurScope(), II, IILoc, II == Ident_super,
NextToken().is(tok::period), ReceiverType)) {
case Sema::ObjCSuperMessage:
CheckArrayDesignatorSyntax(*this, StartLoc, Desig);
return ParseAssignmentExprWithObjCMessageExprStart(
StartLoc, ConsumeToken(), nullptr, nullptr);
case Sema::ObjCClassMessage:
CheckArrayDesignatorSyntax(*this, StartLoc, Desig);
ConsumeToken(); // the identifier
if (!ReceiverType) {
SkipUntil(tok::r_square, StopAtSemi);
return ExprError();
}
// Parse type arguments and protocol qualifiers.
if (Tok.is(tok::less)) {
SourceLocation NewEndLoc;
TypeResult NewReceiverType
= parseObjCTypeArgsAndProtocolQualifiers(IILoc, ReceiverType,
/*consumeLastToken=*/true,
NewEndLoc);
if (!NewReceiverType.isUsable()) {
SkipUntil(tok::r_square, StopAtSemi);
return ExprError();
}
ReceiverType = NewReceiverType.get();
}
return ParseAssignmentExprWithObjCMessageExprStart(StartLoc,
SourceLocation(),
ReceiverType,
nullptr);
case Sema::ObjCInstanceMessage:
// Fall through; we'll just parse the expression and
// (possibly) treat this like an Objective-C message send
// later.
break;
}
}
// Parse the index expression, if we haven't already gotten one
// above (which can only happen in Objective-C++).
// Note that we parse this as an assignment expression, not a constant
// expression (allowing *=, =, etc) to handle the objc case. Sema needs
// to validate that the expression is a constant.
// FIXME: We also need to tell Sema that we're in a
// potentially-potentially evaluated context.
if (!Idx.get()) {
示例7: ParseExpr
/// ParseExpr - Parse an expression with the given \arg
/// ExpectedType. \arg ExpectedType can be invalid if the type cannot
/// be inferred from the context.
///
/// expr = false | true
/// expr = <constant>
/// expr = <identifier>
/// expr = [<identifier>:] paren-expr
ExprResult ParserImpl::ParseExpr(TypeResult ExpectedType) {
// FIXME: Is it right to need to do this here?
if (Tok.kind == Token::EndOfFile) {
Error("unexpected end of file.");
return ExprResult();
}
if (Tok.kind == Token::KWFalse || Tok.kind == Token::KWTrue) {
bool Value = Tok.kind == Token::KWTrue;
ConsumeToken();
return ExprResult(Builder->Constant(Value, Expr::Bool));
}
if (Tok.kind == Token::Number) {
if (!ExpectedType.isValid()) {
Error("cannot infer type of number.");
ConsumeToken();
return ExprResult();
}
return ParseNumber(ExpectedType.get());
}
const Identifier *Label = 0;
if (Tok.kind == Token::Identifier) {
Token LTok = Tok;
Label = GetOrCreateIdentifier(Tok);
ConsumeToken();
if (Tok.kind != Token::Colon) {
ExprSymTabTy::iterator it = ExprSymTab.find(Label);
if (it == ExprSymTab.end()) {
Error("invalid expression label reference.", LTok);
return ExprResult();
}
return it->second;
}
ConsumeToken();
if (ExprSymTab.count(Label)) {
Error("duplicate expression label definition.", LTok);
Label = 0;
}
}
Token Start = Tok;
ExprResult Res = ParseParenExpr(ExpectedType);
if (!Res.isValid()) {
// If we know the type, define the identifier just so we don't get
// use-of-undef errors.
// FIXME: Maybe we should let the symbol table map to invalid
// entries?
if (Label && ExpectedType.isValid()) {
ref<Expr> Value = Builder->Constant(0, ExpectedType.get());
ExprSymTab.insert(std::make_pair(Label, Value));
}
return Res;
} else if (ExpectedType.isValid()) {
// Type check result.
if (Res.get()->getWidth() != ExpectedType.get()) {
// FIXME: Need more info, and range
Error("expression has incorrect type.", Start);
return ExprResult();
}
}
if (Label)
ExprSymTab.insert(std::make_pair(Label, Res.get()));
return Res;
}
示例8: ConsumeExpectedToken
/// ParseArrayDecl - Parse an array declaration. The lexer should be positioned
/// at the opening 'array'.
///
/// array-declaration = "array" name "[" [ size ] "]" ":" domain "->" range
/// "=" array-initializer
/// array-initializer = "symbolic" | "{" { numeric-literal } "}"
DeclResult ParserImpl::ParseArrayDecl() {
// FIXME: Recovery here is horrible, we need to scan to next decl start or
// something.
ConsumeExpectedToken(Token::KWArray);
if (Tok.kind != Token::Identifier) {
Error("expected identifier token.");
return DeclResult();
}
Token Name = Tok;
IntegerResult Size;
TypeResult DomainType;
TypeResult RangeType;
std::vector< ref<ConstantExpr> > Values;
ConsumeToken();
if (Tok.kind != Token::LSquare) {
Error("expected '['.");
goto exit;
}
ConsumeLSquare();
if (Tok.kind != Token::RSquare) {
Size = ParseIntegerConstant(64);
}
if (Tok.kind != Token::RSquare) {
Error("expected ']'.");
goto exit;
}
ConsumeRSquare();
if (Tok.kind != Token::Colon) {
Error("expected ':'.");
goto exit;
}
ConsumeExpectedToken(Token::Colon);
DomainType = ParseTypeSpecifier();
if (Tok.kind != Token::Arrow) {
Error("expected '->'.");
goto exit;
}
ConsumeExpectedToken(Token::Arrow);
RangeType = ParseTypeSpecifier();
if (Tok.kind != Token::Equals) {
Error("expected '='.");
goto exit;
}
ConsumeExpectedToken(Token::Equals);
if (Tok.kind == Token::KWSymbolic) {
ConsumeExpectedToken(Token::KWSymbolic);
} else if (Tok.kind == Token::LSquare) {
ConsumeLSquare();
while (Tok.kind != Token::RSquare) {
if (Tok.kind == Token::EndOfFile) {
Error("unexpected end of file.");
goto exit;
}
ExprResult Res = ParseNumber(RangeType.get());
if (Res.isValid())
Values.push_back(cast<ConstantExpr>(Res.get()));
}
ConsumeRSquare();
} else {
Error("expected 'symbolic' or '['.");
goto exit;
}
// Type check size.
if (!Size.isValid()) {
if (Values.empty()) {
Error("unsized arrays are not yet supported.");
Size = 1;
} else {
Size = Values.size();
}
}
if (!Values.empty()) {
if (Size.get() != Values.size()) {
// FIXME: Lame message.
Error("constant arrays must be completely specified.");
Values.clear();
}
// for (unsigned i = 0; i != Size.get(); ++i) {
// TODO: Check: Must be constant expression.
//}
}
//.........这里部分代码省略.........
示例9: assert
/// TryAnnotateTypeOrScopeToken - If the current token position is on a
/// typename (possibly qualified in C++) or a C++ scope specifier not followed
/// by a typename, TryAnnotateTypeOrScopeToken will replace one or more tokens
/// with a single annotation token representing the typename or C++ scope
/// respectively.
/// This simplifies handling of C++ scope specifiers and allows efficient
/// backtracking without the need to re-parse and resolve nested-names and
/// typenames.
/// It will mainly be called when we expect to treat identifiers as typenames
/// (if they are typenames). For example, in C we do not expect identifiers
/// inside expressions to be treated as typenames so it will not be called
/// for expressions in C.
/// The benefit for C/ObjC is that a typename will be annotated and
/// Actions.getTypeName will not be needed to be called again (e.g. getTypeName
/// will not be called twice, once to check whether we have a declaration
/// specifier, and another one to get the actual type inside
/// ParseDeclarationSpecifiers).
///
/// This returns true if the token was annotated or an unrecoverable error
/// occurs.
///
/// Note that this routine emits an error if you call it with ::new or ::delete
/// as the current tokens, so only call it in contexts where these are invalid.
bool Parser::TryAnnotateTypeOrScopeToken() {
assert((Tok.is(tok::identifier) || Tok.is(tok::coloncolon)
|| Tok.is(tok::kw_typename)) &&
"Cannot be a type or scope token!");
if (Tok.is(tok::kw_typename)) {
// Parse a C++ typename-specifier, e.g., "typename T::type".
//
// typename-specifier:
// 'typename' '::' [opt] nested-name-specifier identifier
// 'typename' '::' [opt] nested-name-specifier template [opt]
// simple-template-id
SourceLocation TypenameLoc = ConsumeToken();
CXXScopeSpec SS;
bool HadNestedNameSpecifier = ParseOptionalCXXScopeSpecifier(SS);
if (!HadNestedNameSpecifier) {
Diag(Tok.getLocation(), diag::err_expected_qualified_after_typename);
return false;
}
TypeResult Ty;
if (Tok.is(tok::identifier)) {
// FIXME: check whether the next token is '<', first!
Ty = Actions.ActOnTypenameType(TypenameLoc, SS, *Tok.getIdentifierInfo(),
Tok.getLocation());
} else if (Tok.is(tok::annot_template_id)) {
TemplateIdAnnotation *TemplateId
= static_cast<TemplateIdAnnotation *>(Tok.getAnnotationValue());
if (TemplateId->Kind == TNK_Function_template) {
Diag(Tok, diag::err_typename_refers_to_non_type_template)
<< Tok.getAnnotationRange();
return false;
}
AnnotateTemplateIdTokenAsType(0);
assert(Tok.is(tok::annot_typename) &&
"AnnotateTemplateIdTokenAsType isn't working properly");
if (Tok.getAnnotationValue())
Ty = Actions.ActOnTypenameType(TypenameLoc, SS, SourceLocation(),
Tok.getAnnotationValue());
else
Ty = true;
} else {
Diag(Tok, diag::err_expected_type_name_after_typename)
<< SS.getRange();
return false;
}
Tok.setKind(tok::annot_typename);
Tok.setAnnotationValue(Ty.isInvalid()? 0 : Ty.get());
Tok.setAnnotationEndLoc(Tok.getLocation());
Tok.setLocation(TypenameLoc);
PP.AnnotateCachedTokens(Tok);
return true;
}
CXXScopeSpec SS;
if (getLang().CPlusPlus)
ParseOptionalCXXScopeSpecifier(SS);
if (Tok.is(tok::identifier)) {
// Determine whether the identifier is a type name.
if (TypeTy *Ty = Actions.getTypeName(*Tok.getIdentifierInfo(),
Tok.getLocation(), CurScope, &SS)) {
// This is a typename. Replace the current token in-place with an
// annotation type token.
Tok.setKind(tok::annot_typename);
Tok.setAnnotationValue(Ty);
Tok.setAnnotationEndLoc(Tok.getLocation());
if (SS.isNotEmpty()) // it was a C++ qualified type name.
Tok.setLocation(SS.getBeginLoc());
// In case the tokens were cached, have Preprocessor replace
// them with the annotation token.
PP.AnnotateCachedTokens(Tok);
return true;
}
//.........这里部分代码省略.........