diff --git a/flang/lib/Parser/prescan.cpp b/flang/lib/Parser/prescan.cpp index 755cb18cb8caf..91c10b2e48cf7 100644 --- a/flang/lib/Parser/prescan.cpp +++ b/flang/lib/Parser/prescan.cpp @@ -875,11 +875,24 @@ bool Prescanner::HandleExponent(TokenSequence &tokens) { } bool Prescanner::HandleKindSuffix(TokenSequence &tokens) { - if (*at_ == '_' && IsLegalInIdentifier(*SkipWhiteSpace(at_ + 1))) { - EmitCharAndAdvance(tokens, *at_); - if (IsLegalIdentifierStart(*at_)) { - // The kind specifier might be a macro, so put it into its own token. + if (*at_ == '_' && IsLegalInIdentifier(at_[1])) { + // The kind specifier might be a macro (with or without its leading + // underscore); put it into its own token if it has been defined. + const char *p{at_ + 1}; + while (IsLegalInIdentifier(*++p)) { + } + if (CharBlock id{at_, static_cast(p - at_)}; + preprocessor_.IsNameDefined(id)) { + // In 1.0e0_foo, "_foo" is a defined name; retain the + // underscore tokens.CloseToken(); + } else { + EmitCharAndAdvance(tokens, '_'); + if (CharBlock id{at_, static_cast(p - at_)}; + preprocessor_.IsNameDefined(id)) { + // In 1.0e0_foo, "foo" is a defined name + tokens.CloseToken(); + } } while (IsLegalInIdentifier(*at_)) { EmitCharAndAdvance(tokens, *at_); diff --git a/flang/lib/Parser/token-sequence.cpp b/flang/lib/Parser/token-sequence.cpp index cdbe89b1eb441..c3016707b8ebf 100644 --- a/flang/lib/Parser/token-sequence.cpp +++ b/flang/lib/Parser/token-sequence.cpp @@ -187,7 +187,7 @@ TokenSequence &TokenSequence::ToLowerCase() { } else if (*p == 'h' || *p == 'H') { // Hollerith *p = 'h'; - } else if (*p == '_') { + } else if (*p == '_' && p + 1 < limit && (p[1] == '"' || p[1] == '\'')) { // kind-prefixed character literal (e.g., 1_"ABC") } else { // exponent diff --git a/flang/test/Preprocessing/kind-suffix.F90 b/flang/test/Preprocessing/kind-suffix.F90 index 36aa323630c6c..ea2a3daaed40d 100644 --- a/flang/test/Preprocessing/kind-suffix.F90 +++ b/flang/test/Preprocessing/kind-suffix.F90 @@ -1,6 +1,9 @@ ! RUN: %flang -E %s 2>&1 | FileCheck %s #define n k +#define _m _p parameter(n=4) !CHECK: print *,1_k print *,1_n +!CHECK: print *,1_p +print *,1_m end