@@ -1241,19 +1241,6 @@ static bool diagnoseZeroWidthMatchAndAdvance(char Target, const char *&CurPtr,
1241
1241
return *CurPtr == Target && CurPtr++;
1242
1242
}
1243
1243
1244
- // / advanceIfMultilineDelimiter - Centralized check for multiline delimiter.
1245
- static bool advanceIfMultilineDelimiter (const char *&CurPtr,
1246
- DiagnosticEngine *Diags) {
1247
- const char *TmpPtr = CurPtr;
1248
- if (*(TmpPtr - 1 ) == ' "' &&
1249
- diagnoseZeroWidthMatchAndAdvance (' "' , TmpPtr, Diags) &&
1250
- diagnoseZeroWidthMatchAndAdvance (' "' , TmpPtr, Diags)) {
1251
- CurPtr = TmpPtr;
1252
- return true ;
1253
- }
1254
- return false ;
1255
- }
1256
-
1257
1244
// / advanceIfCustomDelimiter - Extracts/detects any custom delimiter on
1258
1245
// / opening a string literal, advances CurPtr if a delimiter is found and
1259
1246
// / returns a non-zero delimiter length. CurPtr[-1] must be '#' when called.
@@ -1300,6 +1287,37 @@ static bool delimiterMatches(unsigned CustomDelimiterLen, const char *&BytesPtr,
1300
1287
return true ;
1301
1288
}
1302
1289
1290
+ // / advanceIfMultilineDelimiter - Centralized check for multiline delimiter.
1291
+ static bool advanceIfMultilineDelimiter (unsigned CustomDelimiterLen,
1292
+ const char *&CurPtr,
1293
+ DiagnosticEngine *Diags,
1294
+ bool IsOpening = false ) {
1295
+
1296
+ // Test for single-line string literals that resemble multiline delimiter.
1297
+ const char *TmpPtr = CurPtr + 1 ;
1298
+ if (IsOpening && CustomDelimiterLen) {
1299
+ while (*TmpPtr != ' \r ' && *TmpPtr != ' \n ' ) {
1300
+ if (*TmpPtr == ' "' ) {
1301
+ if (delimiterMatches (CustomDelimiterLen, ++TmpPtr, nullptr )) {
1302
+ return false ;
1303
+ }
1304
+ continue ;
1305
+ }
1306
+ ++TmpPtr;
1307
+ }
1308
+ }
1309
+
1310
+ TmpPtr = CurPtr;
1311
+ if (*(TmpPtr - 1 ) == ' "' &&
1312
+ diagnoseZeroWidthMatchAndAdvance (' "' , TmpPtr, Diags) &&
1313
+ diagnoseZeroWidthMatchAndAdvance (' "' , TmpPtr, Diags)) {
1314
+ CurPtr = TmpPtr;
1315
+ return true ;
1316
+ }
1317
+
1318
+ return false ;
1319
+ }
1320
+
1303
1321
// / lexCharacter - Read a character and return its UTF32 code. If this is the
1304
1322
// / end of enclosing string/character sequence (i.e. the character is equal to
1305
1323
// / 'StopQuote'), this returns ~0U and advances 'CurPtr' pointing to the end of
@@ -1342,7 +1360,8 @@ unsigned Lexer::lexCharacter(const char *&CurPtr, char StopQuote,
1342
1360
1343
1361
DiagnosticEngine *D = EmitDiagnostics ? Diags : nullptr ;
1344
1362
auto TmpPtr = CurPtr;
1345
- if (IsMultilineString && !advanceIfMultilineDelimiter (TmpPtr, D))
1363
+ if (IsMultilineString &&
1364
+ !advanceIfMultilineDelimiter (CustomDelimiterLen, TmpPtr, D))
1346
1365
return ' "' ;
1347
1366
if (CustomDelimiterLen &&
1348
1367
!delimiterMatches (CustomDelimiterLen, TmpPtr, D, /* IsClosing=*/ true ))
@@ -1478,7 +1497,9 @@ static const char *skipToEndOfInterpolatedExpression(const char *CurPtr,
1478
1497
if (!inStringLiteral ()) {
1479
1498
// Open string literal.
1480
1499
OpenDelimiters.push_back (CurPtr[-1 ]);
1481
- AllowNewline.push_back (advanceIfMultilineDelimiter (CurPtr, nullptr ));
1500
+ AllowNewline.push_back (advanceIfMultilineDelimiter (CustomDelimiterLen,
1501
+ CurPtr, nullptr ,
1502
+ true ));
1482
1503
CustomDelimiter.push_back (CustomDelimiterLen);
1483
1504
continue ;
1484
1505
}
@@ -1490,7 +1511,8 @@ static const char *skipToEndOfInterpolatedExpression(const char *CurPtr,
1490
1511
continue ;
1491
1512
1492
1513
// Multi-line string can only be closed by '"""'.
1493
- if (AllowNewline.back () && !advanceIfMultilineDelimiter (CurPtr, nullptr ))
1514
+ if (AllowNewline.back () &&
1515
+ !advanceIfMultilineDelimiter (CustomDelimiterLen, CurPtr, nullptr ))
1494
1516
continue ;
1495
1517
1496
1518
// Check whether we have equivalent number of '#'s.
@@ -1827,7 +1849,8 @@ void Lexer::lexStringLiteral(unsigned CustomDelimiterLen) {
1827
1849
// diagnostics about changing them to double quotes.
1828
1850
assert ((QuoteChar == ' "' || QuoteChar == ' \' ' ) && " Unexpected start" );
1829
1851
1830
- bool IsMultilineString = advanceIfMultilineDelimiter (CurPtr, Diags);
1852
+ bool IsMultilineString = advanceIfMultilineDelimiter (CustomDelimiterLen,
1853
+ CurPtr, Diags, true );
1831
1854
if (IsMultilineString && *CurPtr != ' \n ' && *CurPtr != ' \r ' )
1832
1855
diagnose (CurPtr, diag::lex_illegal_multiline_string_start)
1833
1856
.fixItInsert (Lexer::getSourceLoc (CurPtr), " \n " );
0 commit comments