From f65d756bff8d4c5cbc15bd0322a2ae8e6b896a21 Mon Sep 17 00:00:00 2001 From: Ellie Hermaszewska Date: Tue, 29 Oct 2024 14:49:26 +0800 Subject: format * format * Minor test fixes * enable checking cpp format in ci --- source/slang/slang-check-type.cpp | 716 +++++++++++++++++++------------------- 1 file changed, 361 insertions(+), 355 deletions(-) (limited to 'source/slang/slang-check-type.cpp') diff --git a/source/slang/slang-check-type.cpp b/source/slang/slang-check-type.cpp index eeee13561..34f16751b 100644 --- a/source/slang/slang-check-type.cpp +++ b/source/slang/slang-check-type.cpp @@ -6,467 +6,473 @@ namespace Slang { - Type* checkProperType( - Linkage* linkage, - TypeExp typeExp, - DiagnosticSink* sink) - { - SharedSemanticsContext sharedSemanticsContext( - linkage, - nullptr, - sink); - SemanticsVisitor visitor(&sharedSemanticsContext); +Type* checkProperType(Linkage* linkage, TypeExp typeExp, DiagnosticSink* sink) +{ + SharedSemanticsContext sharedSemanticsContext(linkage, nullptr, sink); + SemanticsVisitor visitor(&sharedSemanticsContext); - SLANG_AST_BUILDER_RAII(linkage->getASTBuilder()); + SLANG_AST_BUILDER_RAII(linkage->getASTBuilder()); - auto typeOut = visitor.CheckProperType(typeExp); - return typeOut.type; - } + auto typeOut = visitor.CheckProperType(typeExp); + return typeOut.type; +} - Type* getPointedToTypeIfCanImplicitDeref(Type* type) +Type* getPointedToTypeIfCanImplicitDeref(Type* type) +{ + if (auto ptrLike = as(type)) { - if (auto ptrLike = as(type)) - { - return ptrLike->getElementType(); - } - else if (auto ptrType = as(type)) - { - return ptrType->getValueType(); - } - else if (auto refType = as(type)) - { - return refType->getValueType(); - } - return nullptr; + return ptrLike->getElementType(); } - - Expr* SemanticsVisitor::TranslateTypeNodeImpl(Expr* node) + else if (auto ptrType = as(type)) { - if (!node) return nullptr; - - auto expr = CheckTerm(node); - expr = ExpectATypeRepr(expr); - return expr; + return ptrType->getValueType(); } - - Type* SemanticsVisitor::ExtractTypeFromTypeRepr(Expr* typeRepr) + else if (auto refType = as(type)) { - if (!typeRepr) return nullptr; - if (auto typeType = as(typeRepr->type)) - { - return typeType->getType(); - } - return m_astBuilder->getErrorType(); + return refType->getValueType(); } + return nullptr; +} + +Expr* SemanticsVisitor::TranslateTypeNodeImpl(Expr* node) +{ + if (!node) + return nullptr; + + auto expr = CheckTerm(node); + expr = ExpectATypeRepr(expr); + return expr; +} - Type* SemanticsVisitor::TranslateTypeNode(Expr* node) +Type* SemanticsVisitor::ExtractTypeFromTypeRepr(Expr* typeRepr) +{ + if (!typeRepr) + return nullptr; + if (auto typeType = as(typeRepr->type)) { - if (!node) return nullptr; - auto typeRepr = TranslateTypeNodeImpl(node); - return ExtractTypeFromTypeRepr(typeRepr); + return typeType->getType(); } + return m_astBuilder->getErrorType(); +} - TypeExp SemanticsVisitor::TranslateTypeNodeForced(TypeExp const& typeExp) - { - auto typeRepr = TranslateTypeNodeImpl(typeExp.exp); +Type* SemanticsVisitor::TranslateTypeNode(Expr* node) +{ + if (!node) + return nullptr; + auto typeRepr = TranslateTypeNodeImpl(node); + return ExtractTypeFromTypeRepr(typeRepr); +} - TypeExp result; - result.exp = typeRepr; - result.type = ExtractTypeFromTypeRepr(typeRepr); - return result; - } +TypeExp SemanticsVisitor::TranslateTypeNodeForced(TypeExp const& typeExp) +{ + auto typeRepr = TranslateTypeNodeImpl(typeExp.exp); + + TypeExp result; + result.exp = typeRepr; + result.type = ExtractTypeFromTypeRepr(typeRepr); + return result; +} - TypeExp SemanticsVisitor::TranslateTypeNode(TypeExp const& typeExp) +TypeExp SemanticsVisitor::TranslateTypeNode(TypeExp const& typeExp) +{ + // HACK(tfoley): It seems that in some cases we end up re-checking + // syntax that we've already checked. We need to root-cause that + // issue, but for now a quick fix in this case is to early + // exist if we've already got a type associated here: + if (typeExp.type) { - // HACK(tfoley): It seems that in some cases we end up re-checking - // syntax that we've already checked. We need to root-cause that - // issue, but for now a quick fix in this case is to early - // exist if we've already got a type associated here: - if (typeExp.type) - { - return typeExp; - } - return TranslateTypeNodeForced(typeExp); + return typeExp; } + return TranslateTypeNodeForced(typeExp); +} - Type* SemanticsVisitor::getRemovedModifierType(ModifiedType* modifiedType, ModifierVal* modifier) +Type* SemanticsVisitor::getRemovedModifierType(ModifiedType* modifiedType, ModifierVal* modifier) +{ + if (modifiedType->getModifierCount() == 1) + return modifiedType->getBase(); + List newModifiers; + for (Index i = 0; i < modifiedType->getModifierCount(); i++) { - if (modifiedType->getModifierCount() == 1) - return modifiedType->getBase(); - List newModifiers; - for (Index i = 0; i < modifiedType->getModifierCount(); i++) - { - auto m = modifiedType->getModifier(i); - if (m == modifier) - continue; - newModifiers.add(m); - } - return m_astBuilder->getModifiedType(modifiedType->getBase(), newModifiers); + auto m = modifiedType->getModifier(i); + if (m == modifier) + continue; + newModifiers.add(m); } + return m_astBuilder->getModifiedType(modifiedType->getBase(), newModifiers); +} - Expr* SemanticsVisitor::ExpectATypeRepr(Expr* expr) +Expr* SemanticsVisitor::ExpectATypeRepr(Expr* expr) +{ + if (auto overloadedExpr = as(expr)) { - if (auto overloadedExpr = as(expr)) - { - expr = resolveOverloadedExpr(overloadedExpr, LookupMask::type); - } - - if (const auto typeType = as(expr->type)) - { - return expr; - } - else if (const auto errorType = as(expr->type)) - { - return expr; - } - - getSink()->diagnose(expr, Diagnostics::expectedAType, expr->type); - return CreateErrorExpr(expr); + expr = resolveOverloadedExpr(overloadedExpr, LookupMask::type); } - Type* SemanticsVisitor::ExpectAType(Expr* expr) + if (const auto typeType = as(expr->type)) { - auto typeRepr = ExpectATypeRepr(expr); - if (auto typeType = as(typeRepr->type)) - { - return typeType->getType(); - } - return m_astBuilder->getErrorType(); + return expr; } - - Type* SemanticsVisitor::ExtractGenericArgType(Expr* exp) + else if (const auto errorType = as(expr->type)) { - return ExpectAType(exp); + return expr; } - IntVal* SemanticsVisitor::ExtractGenericArgInteger(Expr* exp, Type* genericParamType, DiagnosticSink* sink) + getSink()->diagnose(expr, Diagnostics::expectedAType, expr->type); + return CreateErrorExpr(expr); +} + +Type* SemanticsVisitor::ExpectAType(Expr* expr) +{ + auto typeRepr = ExpectATypeRepr(expr); + if (auto typeType = as(typeRepr->type)) { - IntVal* val = CheckIntegerConstantExpression( - exp, - genericParamType ? IntegerConstantExpressionCoercionType::SpecificType - : IntegerConstantExpressionCoercionType::AnyInteger, - genericParamType, - ConstantFoldingKind::LinkTime, - sink); - if(val) return val; - - // If the argument expression could not be coerced to an integer - // constant expression in context, then we will instead construct - // a dummy "error" value to represent the result. - // - val = m_astBuilder->getOrCreate(m_astBuilder->getIntType()); - return val; + return typeType->getType(); } + return m_astBuilder->getErrorType(); +} + +Type* SemanticsVisitor::ExtractGenericArgType(Expr* exp) +{ + return ExpectAType(exp); +} + +IntVal* SemanticsVisitor::ExtractGenericArgInteger( + Expr* exp, + Type* genericParamType, + DiagnosticSink* sink) +{ + IntVal* val = CheckIntegerConstantExpression( + exp, + genericParamType ? IntegerConstantExpressionCoercionType::SpecificType + : IntegerConstantExpressionCoercionType::AnyInteger, + genericParamType, + ConstantFoldingKind::LinkTime, + sink); + if (val) + return val; + + // If the argument expression could not be coerced to an integer + // constant expression in context, then we will instead construct + // a dummy "error" value to represent the result. + // + val = m_astBuilder->getOrCreate(m_astBuilder->getIntType()); + return val; +} - IntVal* SemanticsVisitor::ExtractGenericArgInteger(Expr* exp, Type* genericParamType) +IntVal* SemanticsVisitor::ExtractGenericArgInteger(Expr* exp, Type* genericParamType) +{ + return ExtractGenericArgInteger(exp, genericParamType, getSink()); +} + +Val* SemanticsVisitor::ExtractGenericArgVal(Expr* exp) +{ + if (auto overloadedExpr = as(exp)) { - return ExtractGenericArgInteger(exp, genericParamType, getSink()); + // assume that if it is overloaded, we want a type + exp = resolveOverloadedExpr(overloadedExpr, LookupMask::type); } - - Val* SemanticsVisitor::ExtractGenericArgVal(Expr* exp) + if (auto typeType = as(exp->type)) { - if (auto overloadedExpr = as(exp)) - { - // assume that if it is overloaded, we want a type - exp = resolveOverloadedExpr(overloadedExpr, LookupMask::type); - } - if (auto typeType = as(exp->type)) - { - return typeType->getType(); - } - else if (const auto errorType = as(exp->type)) - { - return exp->type.type; - } - else + return typeType->getType(); + } + else if (const auto errorType = as(exp->type)) + { + return exp->type.type; + } + else + { + if (!exp->type.type) { - if (!exp->type.type) - { - CheckExpr(exp); - } - return ExtractGenericArgInteger(exp, nullptr); + CheckExpr(exp); } + return ExtractGenericArgInteger(exp, nullptr); } +} - Type* SemanticsVisitor::InstantiateGenericType( - DeclRef genericDeclRef, - List const& args) +Type* SemanticsVisitor::InstantiateGenericType( + DeclRef genericDeclRef, + List const& args) +{ + List evaledArgs; + + for (auto argExpr : args) { - List evaledArgs; + evaledArgs.add(ExtractGenericArgVal(argExpr)); + } - for (auto argExpr : args) - { - evaledArgs.add(ExtractGenericArgVal(argExpr)); - } + DeclRef innerDeclRef = + m_astBuilder->getGenericAppDeclRef(genericDeclRef, evaledArgs.getArrayView()); + return DeclRefType::create(m_astBuilder, innerDeclRef); +} - DeclRef innerDeclRef = m_astBuilder->getGenericAppDeclRef(genericDeclRef, evaledArgs.getArrayView()); - return DeclRefType::create(m_astBuilder, innerDeclRef); +bool isManagedType(Type* type) +{ + if (auto declRefValueType = as(type)) + { + if (as(declRefValueType->getDeclRef().getDecl())) + return true; + if (as(declRefValueType->getDeclRef().getDecl())) + return true; } + return false; +} - bool isManagedType(Type* type) +bool SemanticsVisitor::CoerceToProperTypeImpl( + TypeExp const& typeExp, + Type** outProperType, + DiagnosticSink* diagSink) +{ + Type* result = nullptr; + Type* type = typeExp.type; + auto originalExpr = typeExp.exp; + auto expr = originalExpr; + if (!type && expr) { - if (auto declRefValueType = as(type)) + expr = maybeResolveOverloadedExpr(expr, LookupMask::type, diagSink); + + if (auto typeType = as(expr->type)) { - if (as(declRefValueType->getDeclRef().getDecl())) - return true; - if (as(declRefValueType->getDeclRef().getDecl())) - return true; + type = typeType->getType(); } - return false; } - bool SemanticsVisitor::CoerceToProperTypeImpl( - TypeExp const& typeExp, - Type** outProperType, - DiagnosticSink* diagSink) + if (!type) { - Type* result = nullptr; - Type* type = typeExp.type; - auto originalExpr = typeExp.exp; - auto expr = originalExpr; - if(!type && expr) + // Only output diagnostic if we have a sink. + if (diagSink) { - expr = maybeResolveOverloadedExpr(expr, LookupMask::type, diagSink); - - if(auto typeType = as(expr->type)) + // This function *can* be called with typeExp with both exp and type = nullptr. + // Previous behavior didn't output a diagnostic if originalExpr was null, so this keeps + // that behavior. + // + // Additional we check for ErrorType on expr, because if it's set a diagnostic has + // already been output via previous code or via maybeResolveOverloadedExpr. + if (originalExpr && (expr == nullptr || as(expr->type) == nullptr)) { - type = typeType->getType(); + // The diagnostic for expectedAType wants to say what it 'got'. + // The solution given here, currently is to just use the node name. + // How useful that might be could depend, and perhaps some other mechanism + // that catagorized 'what' the wrong thing was is. For now this seems sufficient. + // + // Note that use originalExpr (not expr) because we want original expr for + // diagnostic. + + // Get the AST node type info, so we can output a 'got' name + auto info = ASTClassInfo::getInfo(originalExpr->astNodeType); + diagSink->diagnose(originalExpr, Diagnostics::expectedAType, info->m_name); } } - if (!type) + if (outProperType) { - // Only output diagnostic if we have a sink. - if (diagSink) - { - // This function *can* be called with typeExp with both exp and type = nullptr. - // Previous behavior didn't output a diagnostic if originalExpr was null, so this keeps that behavior. - // - // Additional we check for ErrorType on expr, because if it's set a diagnostic has already been output via - // previous code or via maybeResolveOverloadedExpr. - if (originalExpr && (expr == nullptr || as(expr->type) == nullptr)) - { - // The diagnostic for expectedAType wants to say what it 'got'. - // The solution given here, currently is to just use the node name. - // How useful that might be could depend, and perhaps some other mechanism - // that catagorized 'what' the wrong thing was is. For now this seems sufficient. - // - // Note that use originalExpr (not expr) because we want original expr for diagnostic. - - // Get the AST node type info, so we can output a 'got' name - auto info = ASTClassInfo::getInfo(originalExpr->astNodeType); - diagSink->diagnose(originalExpr, Diagnostics::expectedAType, info->m_name); - } - } - - if (outProperType) - { - *outProperType = nullptr; - } - return false; + *outProperType = nullptr; } + return false; + } - if (auto genericDeclRefType = as(type)) - { - // We are using a reference to a generic declaration as a concrete - // type. This means we should substitute in any default parameter values - // if they are available. - // - // TODO(tfoley): A more expressive type system would substitute in - // "fresh" variables and then solve for their values... - // + if (auto genericDeclRefType = as(type)) + { + // We are using a reference to a generic declaration as a concrete + // type. This means we should substitute in any default parameter values + // if they are available. + // + // TODO(tfoley): A more expressive type system would substitute in + // "fresh" variables and then solve for their values... + // - auto genericDeclRef = genericDeclRefType->getDeclRef(); - ensureDecl(genericDeclRef, DeclCheckState::CanSpecializeGeneric); - List args; - List witnessArgs; - for (Decl* member : genericDeclRef.getDecl()->members) + auto genericDeclRef = genericDeclRefType->getDeclRef(); + ensureDecl(genericDeclRef, DeclCheckState::CanSpecializeGeneric); + List args; + List witnessArgs; + for (Decl* member : genericDeclRef.getDecl()->members) + { + if (auto typeParam = as(member)) { - if (auto typeParam = as(member)) - { - if (!typeParam->initType.exp) - { - if (diagSink) - { - diagSink->diagnose(typeExp.exp, Diagnostics::genericTypeNeedsArgs, typeExp); - *outProperType = m_astBuilder->getErrorType(); - } - return false; - } - - // TODO: this is one place where syntax should get cloned! - if (outProperType) - args.add(ExtractGenericArgVal(typeParam->initType.exp)); - } - else if (auto valParam = as(member)) + if (!typeParam->initType.exp) { - if (!valParam->initExpr) + if (diagSink) { - if (diagSink) - { - diagSink->diagnose(typeExp.exp, Diagnostics::unimplemented, "can't fill in default for generic type parameter"); - *outProperType = m_astBuilder->getErrorType(); - } - return false; + diagSink->diagnose(typeExp.exp, Diagnostics::genericTypeNeedsArgs, typeExp); + *outProperType = m_astBuilder->getErrorType(); } - // TODO: this is one place where syntax should get cloned! - if (outProperType) - args.add(ExtractGenericArgVal(valParam->initExpr)); + return false; } - else if (auto constraintParam = as(member)) + + // TODO: this is one place where syntax should get cloned! + if (outProperType) + args.add(ExtractGenericArgVal(typeParam->initType.exp)); + } + else if (auto valParam = as(member)) + { + if (!valParam->initExpr) { - auto genericParam = as(constraintParam->sub.type)->getDeclRef(); - if (!genericParam) - return false; - auto genericTypeParamDecl = as(genericParam.getDecl()); - if (!genericTypeParamDecl) - return false; - auto defaultType = CheckProperType(genericTypeParamDecl->initType); - if (!defaultType) - return false; - auto witness = tryGetSubtypeWitness(defaultType, CheckProperType(constraintParam->sup)); - if (!witness) + if (diagSink) { - // diagnose - getSink()->diagnose( - genericTypeParamDecl->initType.exp, - Diagnostics::typeArgumentDoesNotConformToInterface, - defaultType, - constraintParam->sup); - return false; + diagSink->diagnose( + typeExp.exp, + Diagnostics::unimplemented, + "can't fill in default for generic type parameter"); + *outProperType = m_astBuilder->getErrorType(); } - witnessArgs.add(witness); + return false; } - else + // TODO: this is one place where syntax should get cloned! + if (outProperType) + args.add(ExtractGenericArgVal(valParam->initExpr)); + } + else if (auto constraintParam = as(member)) + { + auto genericParam = as(constraintParam->sub.type)->getDeclRef(); + if (!genericParam) + return false; + auto genericTypeParamDecl = as(genericParam.getDecl()); + if (!genericTypeParamDecl) + return false; + auto defaultType = CheckProperType(genericTypeParamDecl->initType); + if (!defaultType) + return false; + auto witness = + tryGetSubtypeWitness(defaultType, CheckProperType(constraintParam->sup)); + if (!witness) { - // ignore non-parameter members + // diagnose + getSink()->diagnose( + genericTypeParamDecl->initType.exp, + Diagnostics::typeArgumentDoesNotConformToInterface, + defaultType, + constraintParam->sup); + return false; } + witnessArgs.add(witness); } - // Combine args and witnessArgs - args.addRange(witnessArgs); - - result = DeclRefType::create(getASTBuilder(), - getASTBuilder()->getGenericAppDeclRef(genericDeclRef, args.getArrayView())); - } - - // default case: we expect this to already be a proper type - if (!result) - { - result = type; - } - - // Check for invalid types. - // We don't allow pointers to managed types. - if (auto ptrType = as(result)) - { - if (isManagedType(ptrType->getValueType())) + else { - getSink()->diagnose(typeExp.exp, Diagnostics::cannotDefinePtrTypeToManagedResource); + // ignore non-parameter members } } + // Combine args and witnessArgs + args.addRange(witnessArgs); - *outProperType = result; - return true; + result = DeclRefType::create( + getASTBuilder(), + getASTBuilder()->getGenericAppDeclRef(genericDeclRef, args.getArrayView())); } - TypeExp SemanticsVisitor::CoerceToProperType(TypeExp const& typeExp) + // default case: we expect this to already be a proper type + if (!result) { - TypeExp result = typeExp; - CoerceToProperTypeImpl(typeExp, &result.type, getSink()); - return result; + result = type; } - TypeExp SemanticsVisitor::tryCoerceToProperType(TypeExp const& typeExp) + // Check for invalid types. + // We don't allow pointers to managed types. + if (auto ptrType = as(result)) { - TypeExp result = typeExp; - if(!CoerceToProperTypeImpl(typeExp, &result.type, nullptr)) - return TypeExp(); - return result; + if (isManagedType(ptrType->getValueType())) + { + getSink()->diagnose(typeExp.exp, Diagnostics::cannotDefinePtrTypeToManagedResource); + } } - TypeExp SemanticsVisitor::CheckProperType(TypeExp typeExp) - { - return CoerceToProperType(TranslateTypeNode(typeExp)); - } + *outProperType = result; + return true; +} - TypeExp SemanticsVisitor::CoerceToUsableType(TypeExp const& typeExp, Decl* decl) - { - TypeExp result = CoerceToProperType(typeExp); - Type* type = result.type; - if (auto basicType = as(type)) - { - // TODO: `void` shouldn't be a basic type, to make this easier to avoid - if (basicType->getBaseType() == BaseType::Void) - { - // TODO(tfoley): pick the right diagnostic message - getSink()->diagnose(result.exp, Diagnostics::invalidTypeVoid); - result.type = m_astBuilder->getErrorType(); - return result; - } - } +TypeExp SemanticsVisitor::CoerceToProperType(TypeExp const& typeExp) +{ + TypeExp result = typeExp; + CoerceToProperTypeImpl(typeExp, &result.type, getSink()); + return result; +} + +TypeExp SemanticsVisitor::tryCoerceToProperType(TypeExp const& typeExp) +{ + TypeExp result = typeExp; + if (!CoerceToProperTypeImpl(typeExp, &result.type, nullptr)) + return TypeExp(); + return result; +} - // A type pack is not a usable type other than for defining parameters. - if (!as(decl) && isTypePack(type)) +TypeExp SemanticsVisitor::CheckProperType(TypeExp typeExp) +{ + return CoerceToProperType(TranslateTypeNode(typeExp)); +} + +TypeExp SemanticsVisitor::CoerceToUsableType(TypeExp const& typeExp, Decl* decl) +{ + TypeExp result = CoerceToProperType(typeExp); + Type* type = result.type; + if (auto basicType = as(type)) + { + // TODO: `void` shouldn't be a basic type, to make this easier to avoid + if (basicType->getBaseType() == BaseType::Void) { - getSink()->diagnose(typeExp.exp, Diagnostics::improperUseOfType, typeExp.type); + // TODO(tfoley): pick the right diagnostic message + getSink()->diagnose(result.exp, Diagnostics::invalidTypeVoid); result.type = m_astBuilder->getErrorType(); return result; } - return result; } - TypeExp SemanticsVisitor::CheckUsableType(TypeExp typeExp, Decl* decl) + // A type pack is not a usable type other than for defining parameters. + if (!as(decl) && isTypePack(type)) { - return CoerceToUsableType(TranslateTypeNode(typeExp), decl); + getSink()->diagnose(typeExp.exp, Diagnostics::improperUseOfType, typeExp.type); + result.type = m_astBuilder->getErrorType(); + return result; } + return result; +} - bool SemanticsVisitor::ValuesAreEqual( - IntVal* left, - IntVal* right) - { - if(left == right) return true; +TypeExp SemanticsVisitor::CheckUsableType(TypeExp typeExp, Decl* decl) +{ + return CoerceToUsableType(TranslateTypeNode(typeExp), decl); +} + +bool SemanticsVisitor::ValuesAreEqual(IntVal* left, IntVal* right) +{ + if (left == right) + return true; - if(auto leftConst = as(left)) + if (auto leftConst = as(left)) + { + if (auto rightConst = as(right)) { - if(auto rightConst = as(right)) - { - return leftConst->getValue() == rightConst->getValue(); - } + return leftConst->getValue() == rightConst->getValue(); } + } - if(auto leftVar = as(left)) + if (auto leftVar = as(left)) + { + if (auto rightVar = as(right)) { - if(auto rightVar = as(right)) - { - return leftVar->getDeclRef().equals(rightVar->getDeclRef()); - } - else if (const auto rightPoly = as(right)) - { - return right->equals(leftVar); - } + return leftVar->getDeclRef().equals(rightVar->getDeclRef()); } - if (auto leftVar = as(left)) + else if (const auto rightPoly = as(right)) { - return leftVar->equals(right); + return right->equals(leftVar); } - return false; } - - VectorExpressionType* SemanticsVisitor::createVectorType( - Type* elementType, - IntVal* elementCount) + if (auto leftVar = as(left)) { - return m_astBuilder->getVectorType(elementType, elementCount); + return leftVar->equals(right); } + return false; +} + +VectorExpressionType* SemanticsVisitor::createVectorType(Type* elementType, IntVal* elementCount) +{ + return m_astBuilder->getVectorType(elementType, elementCount); +} - Expr* SemanticsExprVisitor::visitSharedTypeExpr(SharedTypeExpr* expr) +Expr* SemanticsExprVisitor::visitSharedTypeExpr(SharedTypeExpr* expr) +{ + if (!expr->type.Ptr()) { - if (!expr->type.Ptr()) - { - expr->base = CheckProperType(expr->base); - expr->type = expr->base.exp->type; - } - return expr; + expr->base = CheckProperType(expr->base); + expr->type = expr->base.exp->type; } - + return expr; } + +} // namespace Slang -- cgit v1.2.3