[flang-commits] [flang] f3d8335 - [flang] Support BIND(C) variable scope check

via flang-commits flang-commits at lists.llvm.org
Tue May 31 08:27:07 PDT 2022


Author: PeixinQiao
Date: 2022-05-31T23:26:00+08:00
New Revision: f3d8335383672df3b3b950a082c2b11a80cbdb9d

URL: https://github.com/llvm/llvm-project/commit/f3d8335383672df3b3b950a082c2b11a80cbdb9d
DIFF: https://github.com/llvm/llvm-project/commit/f3d8335383672df3b3b950a082c2b11a80cbdb9d.diff

LOG: [flang] Support BIND(C) variable scope check

As Fortran 2018 C819, a variable with the BIND attribute shall be declared
in the specification part of a module. Add the support for this check.

Reviewed By: klausler

Differential Revision: https://reviews.llvm.org/D126653

Added: 
    flang/test/Semantics/resolve113.f90

Modified: 
    flang/lib/Semantics/check-declarations.cpp

Removed: 
    


################################################################################
diff  --git a/flang/lib/Semantics/check-declarations.cpp b/flang/lib/Semantics/check-declarations.cpp
index 25f4b29b45cbc..6b559545e448f 100644
--- a/flang/lib/Semantics/check-declarations.cpp
+++ b/flang/lib/Semantics/check-declarations.cpp
@@ -104,7 +104,7 @@ class CheckHelper {
     }
   }
   bool IsResultOkToDiffer(const FunctionResult &);
-  void CheckBindCName(const Symbol &);
+  void CheckBindC(const Symbol &);
   // Check functions for defined I/O procedures
   void CheckDefinedIoProc(
       const Symbol &, const GenericDetails &, GenericKind::DefinedIo);
@@ -236,7 +236,7 @@ void CheckHelper::Check(const Symbol &symbol) {
   if (symbol.attrs().test(Attr::VOLATILE)) {
     CheckVolatile(symbol, derived);
   }
-  CheckBindCName(symbol);
+  CheckBindC(symbol);
   if (isDone) {
     return; // following checks do not apply
   }
@@ -1869,8 +1869,15 @@ static const std::string *DefinesBindCName(const Symbol &symbol) {
   }
 }
 
-// Check that BIND(C) names are distinct
-void CheckHelper::CheckBindCName(const Symbol &symbol) {
+// Check that BIND(C) names are distinct and BIND(C) variable declared in module
+void CheckHelper::CheckBindC(const Symbol &symbol) {
+  if (!symbol.attrs().test(Attr::BIND_C)) {
+    return;
+  }
+  if (symbol.has<ObjectEntityDetails>() && !symbol.owner().IsModule()) {
+    messages_.Say(symbol.name(),
+        "A variable with BIND(C) attribute may only appear in the specification part of a module"_err_en_US);
+  }
   if (const std::string * name{DefinesBindCName(symbol)}) {
     auto pair{bindC_.emplace(*name, symbol)};
     if (!pair.second) {

diff  --git a/flang/test/Semantics/resolve113.f90 b/flang/test/Semantics/resolve113.f90
new file mode 100644
index 0000000000000..9755e280cfeb0
--- /dev/null
+++ b/flang/test/Semantics/resolve113.f90
@@ -0,0 +1,34 @@
+! RUN: %python %S/test_errors.py %s %flang_fc1
+
+module m
+interface
+  module subroutine dump()
+  end subroutine
+end interface
+  integer, bind(c, name="a") :: x1
+  integer, bind(c) :: x2
+end
+
+subroutine sub()
+  !ERROR: A variable with BIND(C) attribute may only appear in the specification part of a module
+  integer, bind(c, name="b") :: x3
+  !ERROR: A variable with BIND(C) attribute may only appear in the specification part of a module
+  integer, bind(c) :: x4
+end
+
+program main
+  !ERROR: A variable with BIND(C) attribute may only appear in the specification part of a module
+  integer, bind(c, name="c") :: x5
+  !ERROR: A variable with BIND(C) attribute may only appear in the specification part of a module
+  integer, bind(c) :: x6
+end
+
+submodule(m) m2
+  !ERROR: A variable with BIND(C) attribute may only appear in the specification part of a module
+  integer, bind(c, name="d") :: x7
+  !ERROR: A variable with BIND(C) attribute may only appear in the specification part of a module
+  integer, bind(c) :: x8
+contains
+  module procedure dump
+  end procedure
+end


        


More information about the flang-commits mailing list