// FIXME: add support for derived types. // FIXME: check default character kind. bool Sema::CheckEquivalenceType(QualType ExpectedType, const Expr *E) { auto ObjectType = E->getType(); if(ObjectType->isArrayType()) ObjectType = ObjectType->asArrayType()->getElementType(); if(ExpectedType->isCharacterType()) { if(!ObjectType->isCharacterType()) { Diags.Report(E->getLocation(), diag::err_typecheck_expected_char_expr) << ObjectType << E->getSourceRange(); return true; } } else if(ExpectedType->isBuiltinType()) { if(IsDefaultBuiltinOrDoublePrecisionType(ExpectedType)) { if(!IsDefaultBuiltinOrDoublePrecisionType(ObjectType)) { Diags.Report(E->getLocation(), diag::err_typecheck_expected_default_kind_expr) << ObjectType << E->getSourceRange(); return true; } } else { if(!AreTypesOfSameKind(ExpectedType, ObjectType)) { Diags.Report(E->getLocation(), diag::err_typecheck_expected_expr_of_type) << ExpectedType << ObjectType << E->getSourceRange(); return true; } } } return false; }
void DataStmtEngine::VisitVarExpr(VarExpr *E) { if(CheckVar(E)) return; auto VD = E->getVarDecl(); auto Type = VD->getType(); if(auto ATy = Type->asArrayType()) { uint64_t ArraySize; if(!ATy->EvaluateSize(ArraySize, Context)) { VisitExpr(E); return; } // Construct an array constructor expression for initializer SmallVector<Expr*, 32> Items(ArraySize); bool IsUsable = true; SourceLocation Loc; auto ElementType = ATy->getElementType(); for(uint64_t I = 0; I < ArraySize; ++I) { if(!HasValues(E)) return; auto Val = getAndCheckAnyValue(ElementType, E); if(Val.isUsable()) { Items[I] = Val.get(); if(!Loc.isValid()) Loc = Val.get()->getLocation(); } else IsUsable = false; } if(IsUsable) { VD->setInit(ArrayConstructorExpr::Create(Context, Loc, Items, Type)); } return; } // single item auto Val = getAndCheckAnyValue(Type, E); if(Val.isUsable()) VD->setInit(Val.get()); }