Skip to content

Commit f099f76

Browse files
authored
[flang] Handle pp-directives better in line continuation (#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 #100730 and #100345.
1 parent 924a7d8 commit f099f76

File tree

2 files changed

+47
-37
lines changed

2 files changed

+47
-37
lines changed

flang/lib/Parser/prescan.cpp

Lines changed: 28 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -207,11 +207,13 @@ void Prescanner::Statement() {
207207
toks.Put(id, GetProvenance(at_));
208208
if (auto replaced{preprocessor_.MacroReplacement(toks, *this)}) {
209209
auto newLineClass{ClassifyLine(*replaced, GetCurrentProvenance())};
210-
disableSourceContinuation_ =
211-
newLineClass.kind != LineClassification::Kind::Source;
212210
if (newLineClass.kind ==
213211
LineClassification::Kind::CompilerDirective) {
214212
directiveSentinel_ = newLineClass.sentinel;
213+
disableSourceContinuation_ = false;
214+
} else {
215+
disableSourceContinuation_ =
216+
newLineClass.kind != LineClassification::Kind::Source;
215217
}
216218
}
217219
}
@@ -1114,39 +1116,33 @@ bool Prescanner::SkipCommentLine(bool afterAmpersand) {
11141116
SkipToEndOfLine();
11151117
omitNewline_ = true;
11161118
}
1117-
return false;
1118-
}
1119-
auto lineClass{ClassifyLine(nextLine_)};
1120-
if (lineClass.kind == LineClassification::Kind::Comment) {
1121-
NextLine();
1122-
return true;
11231119
} else if (inPreprocessorDirective_) {
1124-
return false;
1125-
} else if (afterAmpersand &&
1126-
(lineClass.kind ==
1127-
LineClassification::Kind::ConditionalCompilationDirective ||
1128-
lineClass.kind == LineClassification::Kind::DefinitionDirective ||
1129-
lineClass.kind == LineClassification::Kind::PreprocessorDirective ||
1130-
lineClass.kind == LineClassification::Kind::IncludeDirective ||
1131-
lineClass.kind == LineClassification::Kind::IncludeLine)) {
1132-
SkipToEndOfLine();
1133-
omitNewline_ = true;
1134-
skipLeadingAmpersand_ = true;
1135-
return false;
1136-
} else if (lineClass.kind ==
1137-
LineClassification::Kind::ConditionalCompilationDirective ||
1138-
lineClass.kind == LineClassification::Kind::PreprocessorDirective) {
1139-
// Allow conditional compilation directives (e.g., #ifdef) to affect
1140-
// continuation lines.
1141-
// Allow other preprocessor directives, too, except #include
1142-
// (when it does not follow '&'), #define, and #undef (because
1143-
// they cannot be allowed to affect preceding text on a
1144-
// continued line).
1145-
preprocessor_.Directive(TokenizePreprocessorDirective(), *this);
1146-
return true;
11471120
} else {
1148-
return false;
1121+
auto lineClass{ClassifyLine(nextLine_)};
1122+
if (lineClass.kind == LineClassification::Kind::Comment) {
1123+
NextLine();
1124+
return true;
1125+
} else if (lineClass.kind ==
1126+
LineClassification::Kind::ConditionalCompilationDirective ||
1127+
lineClass.kind == LineClassification::Kind::PreprocessorDirective) {
1128+
// Allow conditional compilation directives (e.g., #ifdef) to affect
1129+
// continuation lines.
1130+
// Allow other preprocessor directives, too, except #include
1131+
// (when it does not follow '&'), #define, and #undef (because
1132+
// they cannot be allowed to affect preceding text on a
1133+
// continued line).
1134+
preprocessor_.Directive(TokenizePreprocessorDirective(), *this);
1135+
return true;
1136+
} else if (afterAmpersand &&
1137+
(lineClass.kind == LineClassification::Kind::DefinitionDirective ||
1138+
lineClass.kind == LineClassification::Kind::IncludeDirective ||
1139+
lineClass.kind == LineClassification::Kind::IncludeLine)) {
1140+
SkipToEndOfLine();
1141+
omitNewline_ = true;
1142+
skipLeadingAmpersand_ = true;
1143+
}
11491144
}
1145+
return false;
11501146
}
11511147

11521148
const char *Prescanner::FixedFormContinuationLine(bool mightNeedSpace) {

flang/test/Preprocessing/line-in-contin.F90

Lines changed: 19 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
1-
! RUN: %flang_fc1 -E %s 2>&1 | FileCheck %s
2-
! CHECK: call foo( 0.)
3-
! CHECK: call foo( 1.)
4-
! CHECK: call foo( 2.)
5-
! CHECK: call foo( 3.)
1+
! RUN: %flang_fc1 -fopenmp -E %s 2>&1 | FileCheck %s
2+
! CHECK: call foo(0.)
3+
! CHECK: call foo(1.)
4+
! CHECK: call foo(2.)
5+
! CHECK: call foo(3.)
6+
! CHECK: !$omp parallel do default(none) private(j)
7+
! CHECK: !$omp end parallel do
68
call foo( &
79
# 100 "bar.h"
810
& 0.)
@@ -17,4 +19,16 @@
1719
# 103 "bar.h"
1820
& 3. &
1921
)
22+
!$omp parallel do &
23+
#ifdef undef
24+
!$omp garbage &
25+
#else
26+
!$omp default(none) &
27+
#endif
28+
!$omp private(j)
29+
do j=1,100
30+
end do
31+
!$omp end &
32+
# 104 "bar.h"
33+
!$omp parallel do
2034
end

0 commit comments

Comments
 (0)