diff --git a/runtime/sema/type.go b/runtime/sema/type.go index 2e3da32671..10c2f4b14c 100644 --- a/runtime/sema/type.go +++ b/runtime/sema/type.go @@ -3606,6 +3606,8 @@ func (t *CompositeType) IsResourceType() bool { return t.Kind == common.CompositeKindResource || // attachments are always the same kind as their base type (t.Kind == common.CompositeKindAttachment && + // this check is necessary to prevent `attachment A for A {}` + // from causing an infinite recursion case here t.baseType != t && t.baseType.IsResourceType()) } diff --git a/runtime/sema/typeannotationstate.go b/runtime/sema/typeannotationstate.go index 0edd6a4a9e..d3f1cac59f 100644 --- a/runtime/sema/typeannotationstate.go +++ b/runtime/sema/typeannotationstate.go @@ -25,7 +25,11 @@ type TypeAnnotationState uint const ( TypeAnnotationStateUnknown TypeAnnotationState = iota TypeAnnotationStateValid + // Resource annotations (@) are invalid on non-resource types (e.g. @Int) TypeAnnotationStateInvalidResourceAnnotation + // Resource types must have a resource annotation (@) TypeAnnotationStateMissingResourceAnnotation + // attachments types must never appear directly as annotations, and instead + // should appear only in reference types: e.g. `&A` or `[&A]` TypeAnnotationStateDirectAttachmentTypeAnnotation )