[flang][parser] Diagnose an invalid space
authorPeter Klausler <pklausler@nvidia.com>
Fri, 6 Jan 2023 01:04:10 +0000 (17:04 -0800)
committerPeter Klausler <pklausler@nvidia.com>
Fri, 27 Jan 2023 22:54:53 +0000 (14:54 -0800)
In free form, don't silently skip over an invalid space between
an underscore and a kind parameter.

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

flang/lib/Parser/Fortran-parsers.cpp
flang/test/Parser/bad-space.f90 [new file with mode: 0644]

index a6bec93517ce73859ba84cad82347a2830610810..1e7d7deed0a4fc0809b3ae7ce8be5a270b61604c 100644 (file)
@@ -230,19 +230,24 @@ TYPE_PARSER(construct<KindSelector>(
         construct<KindSelector>(construct<KindSelector::StarSize>(
             "*" >> digitString64 / spaceCheck))))
 
+constexpr auto noSpace{
+    recovery(withMessage("invalid space"_err_en_US, !" "_ch), space)};
+
 // R707 signed-int-literal-constant -> [sign] int-literal-constant
-TYPE_PARSER(sourced(construct<SignedIntLiteralConstant>(
-    SignedIntLiteralConstantWithoutKind{}, maybe(underscore >> kindParam))))
+TYPE_PARSER(sourced(
+    construct<SignedIntLiteralConstant>(SignedIntLiteralConstantWithoutKind{},
+        maybe(noSpace >> underscore >> noSpace >> kindParam))))
 
 // R708 int-literal-constant -> digit-string [_ kind-param]
 // The negated look-ahead for a trailing underscore prevents misrecognition
 // when the digit string is a numeric kind parameter of a character literal.
-TYPE_PARSER(construct<IntLiteralConstant>(
-    space >> digitString, maybe(underscore >> kindParam) / !underscore))
+TYPE_PARSER(construct<IntLiteralConstant>(space >> digitString,
+    maybe(underscore >> noSpace >> kindParam) / !underscore))
 
 // R709 kind-param -> digit-string | scalar-int-constant-name
 TYPE_PARSER(construct<KindParam>(digitString64) ||
-    construct<KindParam>(scalar(integer(constant(name)))))
+    construct<KindParam>(
+        scalar(integer(constant(sourced(rawName >> construct<Name>()))))))
 
 // R712 sign -> + | -
 // N.B. A sign constitutes a whole token, so a space is allowed in free form
@@ -278,7 +283,7 @@ TYPE_CONTEXT_PARSER("REAL literal constant"_en_US,
                         "."_ch >> digitString >> maybe(exponentPart) >> ok ||
                         digitString >> exponentPart >> ok) >>
                 construct<RealLiteralConstant::Real>()),
-            maybe(underscore >> kindParam)))
+            maybe(noSpace >> underscore >> noSpace >> kindParam)))
 
 // R718 complex-literal-constant -> ( real-part , imag-part )
 TYPE_CONTEXT_PARSER("COMPLEX literal constant"_en_US,
@@ -343,10 +348,10 @@ TYPE_CONTEXT_PARSER(
 // R725 logical-literal-constant ->
 //        .TRUE. [_ kind-param] | .FALSE. [_ kind-param]
 // Also accept .T. and .F. as extensions.
-TYPE_PARSER(construct<LogicalLiteralConstant>(
-                logicalTRUE, maybe(underscore >> kindParam)) ||
+TYPE_PARSER(construct<LogicalLiteralConstant>(logicalTRUE,
+                maybe(noSpace >> underscore >> noSpace >> kindParam)) ||
     construct<LogicalLiteralConstant>(
-        logicalFALSE, maybe(underscore >> kindParam)))
+        logicalFALSE, maybe(noSpace >> underscore >> noSpace >> kindParam)))
 
 // R726 derived-type-def ->
 //        derived-type-stmt [type-param-def-stmt]...
diff --git a/flang/test/Parser/bad-space.f90 b/flang/test/Parser/bad-space.f90
new file mode 100644 (file)
index 0000000..3b086b0
--- /dev/null
@@ -0,0 +1,4 @@
+! RUN: not %flang_fc1 -fsyntax-only %s 2>&1 | FileCheck %s
+! CHECK: 3:8: error: invalid space
+x = 1._ 4
+end