[flang-commits] [flang] [flang] Handle pp-directives better in line continuation (PR #105572)

Peter Klausler via flang-commits flang-commits at lists.llvm.org
Wed Aug 21 12:18:50 PDT 2024


https://github.com/klausler created https://github.com/llvm/llvm-project/pull/105572

The code for detecting and processing some preprocessing directives (conditional compilation and #line) while skipping comments between one source or compiler directive line and its continuations wasn't correctly handling the case of such a directive following an explicit ampersand.

Fixes https://github.com/llvm/llvm-project/issues/100730 and https://github.com/llvm/llvm-project/issues/100345.

>From 3c2e010a99945044538bd649f90d33840c2268aa Mon Sep 17 00:00:00 2001
From: Peter Klausler <pklausler at nvidia.com>
Date: Wed, 21 Aug 2024 11:52:58 -0700
Subject: [PATCH] [flang] Handle pp-directives better in line continuation

The code for detecting and processing some preprocessing directives
(conditional compilation and #line) while skipping comments between
one source or compiler directive line and its continuations wasn't
correctly handling the case of such a directive following an explicit
ampersand.

Fixes https://github.com/llvm/llvm-project/issues/100730 and
https://github.com/llvm/llvm-project/issues/100345.
---
 flang/lib/Parser/prescan.cpp                | 60 ++++++++++-----------
 flang/test/Preprocessing/line-in-contin.F90 | 24 +++++++--
 2 files changed, 47 insertions(+), 37 deletions(-)

diff --git a/flang/lib/Parser/prescan.cpp b/flang/lib/Parser/prescan.cpp
index c01d512b4653de..804ada7d11e020 100644
--- a/flang/lib/Parser/prescan.cpp
+++ b/flang/lib/Parser/prescan.cpp
@@ -207,11 +207,13 @@ void Prescanner::Statement() {
           toks.Put(id, GetProvenance(at_));
           if (auto replaced{preprocessor_.MacroReplacement(toks, *this)}) {
             auto newLineClass{ClassifyLine(*replaced, GetCurrentProvenance())};
-            disableSourceContinuation_ =
-                newLineClass.kind != LineClassification::Kind::Source;
             if (newLineClass.kind ==
                 LineClassification::Kind::CompilerDirective) {
               directiveSentinel_ = newLineClass.sentinel;
+              disableSourceContinuation_ = false;
+            } else {
+              disableSourceContinuation_ =
+                  newLineClass.kind != LineClassification::Kind::Source;
             }
           }
         }
@@ -1114,39 +1116,33 @@ bool Prescanner::SkipCommentLine(bool afterAmpersand) {
       SkipToEndOfLine();
       omitNewline_ = true;
     }
-    return false;
-  }
-  auto lineClass{ClassifyLine(nextLine_)};
-  if (lineClass.kind == LineClassification::Kind::Comment) {
-    NextLine();
-    return true;
   } else if (inPreprocessorDirective_) {
-    return false;
-  } else if (afterAmpersand &&
-      (lineClass.kind ==
-              LineClassification::Kind::ConditionalCompilationDirective ||
-          lineClass.kind == LineClassification::Kind::DefinitionDirective ||
-          lineClass.kind == LineClassification::Kind::PreprocessorDirective ||
-          lineClass.kind == LineClassification::Kind::IncludeDirective ||
-          lineClass.kind == LineClassification::Kind::IncludeLine)) {
-    SkipToEndOfLine();
-    omitNewline_ = true;
-    skipLeadingAmpersand_ = true;
-    return false;
-  } else if (lineClass.kind ==
-          LineClassification::Kind::ConditionalCompilationDirective ||
-      lineClass.kind == LineClassification::Kind::PreprocessorDirective) {
-    // Allow conditional compilation directives (e.g., #ifdef) to affect
-    // continuation lines.
-    // Allow other preprocessor directives, too, except #include
-    // (when it does not follow '&'), #define, and #undef (because
-    // they cannot be allowed to affect preceding text on a
-    // continued line).
-    preprocessor_.Directive(TokenizePreprocessorDirective(), *this);
-    return true;
   } else {
-    return false;
+    auto lineClass{ClassifyLine(nextLine_)};
+    if (lineClass.kind == LineClassification::Kind::Comment) {
+      NextLine();
+      return true;
+    } else if (lineClass.kind ==
+            LineClassification::Kind::ConditionalCompilationDirective ||
+        lineClass.kind == LineClassification::Kind::PreprocessorDirective) {
+      // Allow conditional compilation directives (e.g., #ifdef) to affect
+      // continuation lines.
+      // Allow other preprocessor directives, too, except #include
+      // (when it does not follow '&'), #define, and #undef (because
+      // they cannot be allowed to affect preceding text on a
+      // continued line).
+      preprocessor_.Directive(TokenizePreprocessorDirective(), *this);
+      return true;
+    } else if (afterAmpersand &&
+        (lineClass.kind == LineClassification::Kind::DefinitionDirective ||
+            lineClass.kind == LineClassification::Kind::IncludeDirective ||
+            lineClass.kind == LineClassification::Kind::IncludeLine)) {
+      SkipToEndOfLine();
+      omitNewline_ = true;
+      skipLeadingAmpersand_ = true;
+    }
   }
+  return false;
 }
 
 const char *Prescanner::FixedFormContinuationLine(bool mightNeedSpace) {
diff --git a/flang/test/Preprocessing/line-in-contin.F90 b/flang/test/Preprocessing/line-in-contin.F90
index 138e579bffaa28..28efbd02d3ae89 100644
--- a/flang/test/Preprocessing/line-in-contin.F90
+++ b/flang/test/Preprocessing/line-in-contin.F90
@@ -1,8 +1,10 @@
-! RUN: %flang_fc1 -E %s 2>&1 | FileCheck %s
-! CHECK: call foo( 0.)
-! CHECK: call foo( 1.)
-! CHECK: call foo( 2.)
-! CHECK: call foo( 3.)
+! RUN: %flang_fc1 -fopenmp -E %s 2>&1 | FileCheck %s
+! CHECK: call foo(0.)
+! CHECK: call foo(1.)
+! CHECK: call foo(2.)
+! CHECK: call foo(3.)
+! CHECK: !$omp parallel do default(none) private(j)
+! CHECK: !$omp end parallel do
 call foo( &
 # 100 "bar.h"
          & 0.)
@@ -17,4 +19,16 @@
 # 103 "bar.h"
          & 3. &
     )
+!$omp parallel do &
+#ifdef undef
+!$omp garbage &
+#else
+!$omp default(none) &
+#endif
+!$omp private(j)
+  do j=1,100
+  end do
+!$omp end &
+# 104 "bar.h"
+!$omp parallel do
 end



More information about the flang-commits mailing list