Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Check for constrains C741 through C749 #1100

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 6 additions & 2 deletions lib/Semantics/check-declarations.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -385,12 +385,16 @@ void CheckHelper::CheckObjectEntity(
symbolBeingChecked_ = nullptr;
if (!details.coshape().empty()) {
if (IsAllocatable(symbol)) {
if (!details.coshape().IsDeferredShape()) { // C827
if (!details.coshape().IsDeferredShape()) { // C746, C827
messages_.Say(
"ALLOCATABLE coarray must have a deferred coshape"_err_en_US);
}
} else if (symbol.owner().IsDerivedType()) { // C746
messages_.Say(
"Coarray components must be ALLOCATABLE and have a deferred "
"coshape"_err_en_US);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think the message should say "and have a deferred coshape" unless it doesn't have a deferred coshape.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Or just combine the tests and use the second message, it's got all the information.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, Tim. I'll change the code to remove that phrase when it doesn't apply.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@klausler, I think it's a little confusing to have the message tell the user that the declaration must have a deferred coshape when it already has one. I plan to stick with Tim's suggestion.

} else {
if (!details.coshape().IsAssumedSize()) { // C828
if (!details.coshape().IsAssumedSize()) { // C746, C828
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

C746 applies to components, but components are all handled earlier.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good catch! This also applies to the comment above. I'll remove the spurious references.

messages_.Say(
"Non-ALLOCATABLE coarray must have an explicit coshape"_err_en_US);
}
Expand Down
32 changes: 27 additions & 5 deletions lib/Semantics/resolve-names.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3680,7 +3680,7 @@ bool DeclarationVisitor::Pre(const parser::DerivedTypeDef &x) {
if (symbol->has<TypeParamDetails>() && !paramNames.count(name)) {
SayDerivedType(name,
"'%s' is not a type parameter of this derived type"_err_en_US,
currScope()); // C742
currScope()); // C741
}
}
Walk(std::get<std::list<parser::Statement<parser::PrivateOrSequence>>>(x.t));
Expand Down Expand Up @@ -3821,14 +3821,36 @@ void DeclarationVisitor::Post(const parser::ComponentDecl &x) {
!attrs.HasAny({Attr::PUBLIC, Attr::PRIVATE})) {
attrs.set(Attr::PRIVATE);
}
if (!attrs.HasAny({Attr::POINTER, Attr::ALLOCATABLE})) {
if (const auto *declType{GetDeclTypeSpec()}) {
if (const auto *derived{declType->AsDerived()}) {
if (const auto *declType{GetDeclTypeSpec()}) {
if (const auto *derived{declType->AsDerived()}) {
if (!attrs.HasAny({Attr::POINTER, Attr::ALLOCATABLE})) {
if (derivedTypeInfo_.type == &derived->typeSymbol()) { // C744
Say("Recursive use of the derived type requires "
"POINTER or ALLOCATABLE"_err_en_US);
}
}
if (!coarraySpec().empty()) { // C747
if (IsTeamType(derived)) {
Say("A coarray component may not be of type TEAM_TYPE from "
"ISO_FORTRAN_ENV"_err_en_US);
} else {
if (IsIsoCType(derived)) {
Say("A coarray component may not be of C_PTR or C_FUNPTR from "
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Missing the word "type", or needs rewording.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for catching this. I'll fix it.

"ISO_C_BINDING when an allocatable object is a "
"coarray"_err_en_US);
}
}
}
if (FindCoarrayUltimateComponent(*derived)) { // C748
if (attrs.HasAny({Attr::POINTER, Attr::ALLOCATABLE})) {
Say("A component whose type has a coarray ultimate component "
"cannot be a POINTER or ALLOCATABLE"_err_en_US);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We have mostly been using "may not" rather than "cannot".

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I also use "must not", but I shouldn't -- "may" is the correct modal verb here, since we're talking about what's allowed, not what might be possible.

You might as well capture the result of FindCoarrayUltimateComponent and use its name in the message and link to its declaration.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks. I'll fix it.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I notice that there are many uses of the word "cannot" in resolve-names.cpp. @tskeith, should I fix them all in this pull request?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it makes more sense to change them in a separate pull request, but if you want to do it in this one that's okay too.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think I'll wait.

}
if (!arraySpec().empty() || !coarraySpec().empty()) {
Say("A component whose type has a coarray ultimate component "
"cannot be an array or corray"_err_en_US);
}
}
}
}
if (OkToAddComponent(name)) {
Expand Down Expand Up @@ -4742,7 +4764,7 @@ Symbol *DeclarationVisitor::MakeTypeSymbol(
const SourceName &name, Details &&details) {
Scope &derivedType{currScope()};
CHECK(derivedType.IsDerivedType());
if (auto *symbol{FindInScope(derivedType, name)}) {
if (auto *symbol{FindInScope(derivedType, name)}) { // C742
Say2(name,
"Type parameter, component, or procedure binding '%s'"
" already defined in this type"_err_en_US,
Expand Down
19 changes: 1 addition & 18 deletions test/Semantics/allocate11.f90
Original file line number Diff line number Diff line change
Expand Up @@ -5,19 +5,6 @@

! Rules I should know when working with coarrays and derived type:

! C736: If EXTENDS appears and the type being defined has a coarray ultimate
! component, its parent type shall have a coarray ultimate component.
Comment on lines -8 to -9
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Where is the test for C736 now?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

C736 is specific to the definition of a component of a derived type, and all of the tests in allocate11.f90 were allocate statements. I added the test resolve86.f90 in my previous pull request to cover the case of defining a component that contains a coarray ultimate component without having a parent type that contains a coarray ultimate component. This may have happened after you reviewed and approved that pull request.


! C746: (R737) If a coarray-spec appears, it shall be a deferred-coshape-spec-list
! and the component shall have the ALLOCATABLE attribute.

! C747: If a coarray-spec appears, the component shall not be of type C_PTR or
! C_FUNPTR from the intrinsic module ISO_C_BINDING (18.2), or of type TEAM_TYPE from the
! intrinsic module ISO_FORTRAN_ENV (16.10.2).

! C748: A data component whose type has a coarray ultimate component shall be a
! nonpointer nonallocatable scalar and shall not be a coarray.

! 7.5.4.3 Coarray components
! 7.5.6 Final subroutines: C786

Expand All @@ -38,7 +25,6 @@ subroutine C937(var)

type B
type(A) y
type(B), pointer :: forward
real :: u
end type

Expand All @@ -47,7 +33,7 @@ subroutine C937(var)
end type

type D
type(A), pointer :: potential
type(A) :: potential
end type


Expand All @@ -66,9 +52,6 @@ subroutine C937(var)

! Also, as per C826 or C852, var can only be an allocatable, not a pointer

! OK, x is not an ultimate component
allocate(D:: var)

!ERROR: Type-spec in ALLOCATE must not specify a type with a coarray ultimate component
allocate(A:: var)
!ERROR: Type-spec in ALLOCATE must not specify a type with a coarray ultimate component
Expand Down
2 changes: 1 addition & 1 deletion test/Semantics/call12.f90
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ module m
real, pointer :: p
end type
type :: hasCoarray
real :: co[*]
real, allocatable :: co[:]
end type
contains
pure function test(ptr, in, hpd)
Expand Down
2 changes: 1 addition & 1 deletion test/Semantics/call14.f90
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@

module m
type :: hasCoarray
real :: coarray[*]
real, allocatable :: coarray[:]
end type
contains
!ERROR: VALUE attribute may apply only to a dummy data object
Expand Down
2 changes: 1 addition & 1 deletion test/Semantics/misc-declarations.f90
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ module m
!ERROR: Non-ALLOCATABLE coarray must have an explicit coshape
real :: mustBeExplicit[:] ! C828
type :: hasCoarray
real :: coarray[*]
real, allocatable :: coarray[:]
end type
real :: coarray[*]
type(hasCoarray) :: coarrayComponent
Expand Down
8 changes: 4 additions & 4 deletions test/Semantics/modfile24.f90
Original file line number Diff line number Diff line change
Expand Up @@ -36,8 +36,8 @@ module m2
! coarray-spec in components and with non-constants bounds
module m3
type t
real :: c[1:10,1:*]
complex, codimension[5,*] :: d
real, allocatable :: c[:,:]
complex, allocatable, codimension[:,:] :: d
end type
real, allocatable :: e[:,:,:]
contains
Expand All @@ -50,8 +50,8 @@ subroutine s(a, b, n)
!Expect: m3.mod
!module m3
! type::t
! real(4)::c[1_8:10_8,1_8:*]
! complex(4)::d[1_8:5_8,1_8:*]
! real(4),allocatable::c[:,:]
! complex(4),allocatable::d[:,:]
! end type
! real(4),allocatable::e[:,:,:]
!contains
Expand Down
8 changes: 7 additions & 1 deletion test/Semantics/resolve33.f90
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,13 @@
! Derived type parameters
! C731 The same type-param-name shall not appear more than once in a given
! derived-type-stmt.

! C741 A type-param-name in a type-param-def-stmt in a derived-type-def shall
! be one of the type-paramnames in the derived-type-stmt of that
! derived-type-def.
! C742 Each type-param-name in the derived-type-stmt in a derived-type-def
! shall appear exactly once as a type-param-name in a type-param-def-stmt
! in that derived-type-def .

module m
!ERROR: Duplicate type parameter name: 'a'
type t1(a, b, a)
Expand Down
3 changes: 3 additions & 0 deletions test/Semantics/resolve44.f90
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
! RUN: %B/test/Semantics/test_errors.sh %s %flang %t
! Error tests for recursive use of derived types.
! C744 If neither the POINTER nor the ALLOCATABLE attribute is specified, the
! declaration-type-spec in the component-def-stmt shall specify an intrinsic
! type or a previously defined derived type.

program main
type :: recursive1
Expand Down
73 changes: 73 additions & 0 deletions test/Semantics/resolve88.f90
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
! RUN: %B/test/Semantics/test_errors.sh %s %flang %t
! C746, C747, and C748
module m
use ISO_FORTRAN_ENV
use ISO_C_BINDING

! C746 If a coarray-spec appears, it shall be a deferred-coshape-spec-list and
! the component shall have the ALLOCATABLE attribute.

type testCoArrayType
real, allocatable, codimension[:] :: allocatableField
!ERROR: Coarray components must be ALLOCATABLE and have a deferred coshape
real, codimension[:] :: deferredField
!ERROR: 'pointerfield' may not have the POINTER attribute because it is a coarray
!ERROR: Coarray components must be ALLOCATABLE and have a deferred coshape
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be nice if the wording of these two messages were similar. For example, the second could be:
Component 'pointerfield' must have the ALLOCATABLE attribute because it is a coarray

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds good. I'll change it.

real, pointer, codimension[:] :: pointerField
!ERROR: Coarray components must be ALLOCATABLE and have a deferred coshape
real, codimension[*] :: realField
end type testCoArrayType

! C747 If a coarray-spec appears, the component shall not be of type C_PTR or
! C_FUNPTR from the intrinsic module ISO_C_BINDING (18.2), or of type
! TEAM_TYPE from the intrinsic module ISO_FORTRAN_ENV (16.10.2).

type goodCoarrayType
real, allocatable, codimension[:] :: field
end type goodCoarrayType

type goodTeam_typeCoarrayType
type(team_type), allocatable :: field
end type goodTeam_typeCoarrayType

type goodC_ptrCoarrayType
type(c_ptr), allocatable :: field
end type goodC_ptrCoarrayType

type goodC_funptrCoarrayType
type(c_funptr), allocatable :: field
end type goodC_funptrCoarrayType

type team_typeCoarrayType
!ERROR: A coarray component may not be of type TEAM_TYPE from ISO_FORTRAN_ENV
type(team_type), allocatable, codimension[:] :: field
end type team_typeCoarrayType

type c_ptrCoarrayType
!ERROR: A coarray component may not be of C_PTR or C_FUNPTR from ISO_C_BINDING when an allocatable object is a coarray
type(c_ptr), allocatable, codimension[:] :: field
end type c_ptrCoarrayType

type c_funptrCoarrayType
!ERROR: A coarray component may not be of C_PTR or C_FUNPTR from ISO_C_BINDING when an allocatable object is a coarray
type(c_funptr), allocatable, codimension[:] :: field
end type c_funptrCoarrayType

! C748 A data component whose type has a coarray ultimate component shall be a
! nonpointer nonallocatable scalar and shall not be a coarray.

type coarrayType
real, allocatable, codimension[:] :: goodCoarrayField
end type coarrayType

type testType
type(coarrayType) :: goodField
!ERROR: A component whose type has a coarray ultimate component cannot be a POINTER or ALLOCATABLE
type(coarrayType), pointer :: pointerField
!ERROR: A component whose type has a coarray ultimate component cannot be a POINTER or ALLOCATABLE
type(coarrayType), allocatable :: allocatableField
!ERROR: A component whose type has a coarray ultimate component cannot be an array or corray
type(coarrayType), dimension(3) :: arrayField
end type testType

end module m