diff --git a/flang/lib/Semantics/check-call.cpp b/flang/lib/Semantics/check-call.cpp index 9fad1aa3dd0bf..4708d51d3af4d 100644 --- a/flang/lib/Semantics/check-call.cpp +++ b/flang/lib/Semantics/check-call.cpp @@ -1645,7 +1645,8 @@ static void CheckPresent(evaluate::ActualArguments &arguments, } else { symbol = arg->GetAssumedTypeDummy(); } - if (!symbol || !symbol->attrs().test(semantics::Attr::OPTIONAL)) { + if (!symbol || + !symbol->GetUltimate().attrs().test(semantics::Attr::OPTIONAL)) { messages.Say(arg ? arg->sourceLocation() : messages.at(), "Argument of PRESENT() must be the name of a whole OPTIONAL dummy argument"_err_en_US); } diff --git a/flang/lib/Semantics/resolve-directives.cpp b/flang/lib/Semantics/resolve-directives.cpp index d635a7b8b7874..cc9f1cc7ed269 100644 --- a/flang/lib/Semantics/resolve-directives.cpp +++ b/flang/lib/Semantics/resolve-directives.cpp @@ -2036,20 +2036,21 @@ void OmpAttributeVisitor::Post(const parser::OpenMPAllocatorsConstruct &x) { void OmpAttributeVisitor::Post(const parser::Name &name) { auto *symbol{name.symbol}; auto IsPrivatizable = [](const Symbol *sym) { + auto *misc{sym->detailsIf()}; return !IsProcedure(*sym) && !IsNamedConstant(*sym) && !sym->owner().IsDerivedType() && sym->owner().kind() != Scope::Kind::ImpliedDos && !sym->detailsIf() && - !sym->detailsIf(); + !sym->detailsIf() && + (!misc || + (misc->kind() != MiscDetails::Kind::ComplexPartRe && + misc->kind() != MiscDetails::Kind::ComplexPartIm && + misc->kind() != MiscDetails::Kind::KindParamInquiry && + misc->kind() != MiscDetails::Kind::LenParamInquiry && + misc->kind() != MiscDetails::Kind::ConstructName)); }; if (symbol && !dirContext_.empty() && GetContext().withinConstruct) { - // Exclude construct-names - if (auto *details{symbol->detailsIf()}) { - if (details->kind() == semantics::MiscDetails::Kind::ConstructName) { - return; - } - } if (IsPrivatizable(symbol) && !IsObjectWithDSA(*symbol)) { // TODO: create a separate function to go through the rules for // predetermined, explicitly determined, and implicitly diff --git a/flang/test/Semantics/OpenMP/complex.f90 b/flang/test/Semantics/OpenMP/complex.f90 new file mode 100644 index 0000000000000..62336c7e6b31a --- /dev/null +++ b/flang/test/Semantics/OpenMP/complex.f90 @@ -0,0 +1,13 @@ +! RUN: %flang_fc1 -fopenmp -fsyntax-only %s + +! Check that using %re/%im inside 'parallel' doesn't cause syntax errors. +subroutine test_complex_re_im + complex :: cc(4) = (1,2) + integer :: i + + !$omp parallel do private(cc) + do i = 1, 4 + print *, cc(i)%re, cc(i)%im + end do + !$omp end parallel do +end subroutine diff --git a/flang/test/Semantics/OpenMP/present.f90 b/flang/test/Semantics/OpenMP/present.f90 new file mode 100644 index 0000000000000..31bdcc7a8c654 --- /dev/null +++ b/flang/test/Semantics/OpenMP/present.f90 @@ -0,0 +1,9 @@ +! RUN: %flang_fc1 -fopenmp -fsyntax-only %s + +! Check that using 'present' inside 'parallel' doesn't cause syntax errors. +subroutine test_present(opt) + integer, optional :: opt + !$omp parallel + if (present(opt)) print *, "present" + !$omp end parallel +end subroutine